~drizzle-trunk/drizzle/development

« back to all changes in this revision

Viewing changes to plugin/mysql_protocol/net_serv.cc

  • Committer: Mark Atwood
  • Date: 2011-06-14 19:30:31 UTC
  • mfrom: (2318.2.41 refactor5)
  • Revision ID: me@mark.atwood.name-20110614193031-lwbrlwfgf6id4r8b
merge lp:~olafvdspek/drizzle/refactor6
 with resolved conflict in drizzled/plugin/client.h

Show diffs side-by-side

added added

removed removed

Lines of Context:
60
60
#define COMP_HEADER_SIZE 3              /* compression header extra size */
61
61
 
62
62
#define MAX_PACKET_LENGTH (256L*256L*256L-1)
63
 
const char  *not_error_sqlstate= "00000";
64
63
 
65
 
static bool net_write_buff(NET *net, const unsigned char *packet, uint32_t len);
 
64
static bool net_write_buff(NET*, const void*, uint32_t len);
66
65
static int drizzleclient_net_real_write(NET *net, const unsigned char *packet, size_t len);
67
66
 
68
67
/** Init with packet info. */
69
68
 
70
 
void drizzleclient_net_init(NET *net, Vio* vio, uint32_t buffer_length)
71
 
{
72
 
  net->vio = vio;
73
 
  net->max_packet= (uint32_t) buffer_length;
74
 
  net->max_packet_size= max(buffer_length, drizzled::global_system_variables.max_allowed_packet);
75
 
 
76
 
  net->buff=(unsigned char*) malloc((size_t) net->max_packet + NET_HEADER_SIZE + COMP_HEADER_SIZE);
77
 
  net->buff_end=net->buff+net->max_packet;
78
 
  net->error=0; net->return_status=0;
79
 
  net->pkt_nr=net->compress_pkt_nr=0;
80
 
  net->write_pos=net->read_pos = net->buff;
81
 
  net->last_error[0]=0;
82
 
  net->compress=0; net->reading_or_writing=0;
83
 
  net->where_b = net->remain_in_buf=0;
84
 
  net->last_errno=0;
85
 
  net->unused= 0;
86
 
 
87
 
  if (vio != 0)                    /* If real connection */
88
 
  {
89
 
    net->fd  = vio->get_fd();            /* For perl DBI/DBD */
90
 
    vio->fastsend();
91
 
  }
92
 
}
93
 
 
94
 
void drizzleclient_net_init_sock(NET* net, int sock, uint32_t buffer_length)
95
 
{
96
 
  drizzleclient_net_init(net, new Vio(sock), buffer_length);
97
 
}
98
 
 
99
 
void drizzleclient_net_end(NET *net)
100
 
{
101
 
  free(net->buff);
102
 
  net->buff= NULL;
103
 
}
104
 
 
105
 
void drizzleclient_net_close(NET *net)
106
 
{
107
 
  drizzled::safe_delete(net->vio);
108
 
}
109
 
 
110
 
bool drizzleclient_net_peer_addr(NET *net, char *buf, uint16_t *port, size_t buflen)
111
 
{
112
 
  return net->vio->peer_addr(buf, port, buflen);
113
 
}
114
 
 
115
 
void drizzleclient_net_keepalive(NET *net, bool flag)
116
 
{
117
 
  net->vio->keepalive(flag);
118
 
}
119
 
 
120
 
int drizzleclient_net_get_sd(NET *net)
121
 
{
122
 
  return net->vio->get_fd();
 
69
void NET::init(int sock, uint32_t buffer_length)
 
70
{
 
71
  vio= new Vio(sock);
 
72
  max_packet= (uint32_t) buffer_length;
 
73
  max_packet_size= max(buffer_length, drizzled::global_system_variables.max_allowed_packet);
 
74
 
 
75
  buff= (unsigned char*) malloc((size_t) max_packet + NET_HEADER_SIZE + COMP_HEADER_SIZE);
 
76
  buff_end= buff + max_packet;
 
77
  error_= 0;
 
78
  pkt_nr= compress_pkt_nr= 0;
 
79
  write_pos= read_pos= buff;
 
80
  compress= 0; 
 
81
  where_b= remain_in_buf= 0;
 
82
  last_errno= 0;
 
83
  vio->fastsend();
 
84
}
 
85
 
 
86
void NET::end()
 
87
{
 
88
  free(buff);
 
89
  buff= NULL;
 
90
}
 
91
 
 
92
void NET::close()
 
93
{
 
94
  drizzled::safe_delete(vio);
 
95
}
 
96
 
 
97
bool NET::peer_addr(char *buf, size_t buflen, uint16_t& port)
 
98
{
 
99
  return vio->peer_addr(buf, buflen, port);
 
100
}
 
101
 
 
102
void NET::keepalive(bool flag)
 
103
{
 
104
  vio->keepalive(flag);
 
105
}
 
106
 
 
107
int NET::get_sd() const
 
108
{
 
109
  return vio->get_fd();
123
110
}
124
111
 
125
112
/** Realloc the packet buffer. */
129
116
  if (length >= net->max_packet_size)
130
117
  {
131
118
    /* @todo: 1 and 2 codes are identical. */
132
 
    net->error= 3;
 
119
    net->error_= 3;
133
120
    net->last_errno= ER_NET_PACKET_TOO_LARGE;
134
121
    my_error(ER_NET_PACKET_TOO_LARGE, MYF(0));
135
122
    return 1;
145
132
  return 0;
146
133
}
147
134
 
148
 
bool drizzleclient_net_flush(NET *net)
 
135
bool NET::flush()
149
136
{
150
 
  bool error= 0;
151
 
  if (net->buff != net->write_pos)
 
137
  bool error= false;
 
138
  if (buff != write_pos)
152
139
  {
153
 
    error= drizzleclient_net_real_write(net, net->buff, (size_t) (net->write_pos - net->buff)) ? 1 : 0;
154
 
    net->write_pos= net->buff;
 
140
    error= drizzleclient_net_real_write(this, buff, write_pos - buff) ? true : false;
 
141
    write_pos= buff;
155
142
  }
156
143
  /* Sync packet number if using compression */
157
 
  if (net->compress)
158
 
    net->pkt_nr=net->compress_pkt_nr;
 
144
  if (compress)
 
145
    pkt_nr= compress_pkt_nr;
159
146
  return error;
160
147
}
161
148
 
174
161
   If compression is used the original package is modified!
175
162
*/
176
163
 
177
 
bool
178
 
drizzleclient_net_write(NET *net,const unsigned char *packet,size_t len)
 
164
static bool
 
165
drizzleclient_net_write(NET* net, const void* packet0, size_t len)
179
166
{
 
167
  const unsigned char* packet= reinterpret_cast<const unsigned char*>(packet0);
180
168
  unsigned char buff[NET_HEADER_SIZE];
181
169
  if (unlikely(!net->vio)) /* nowhere to write */
182
170
    return 0;
190
178
    const uint32_t z_size = MAX_PACKET_LENGTH;
191
179
    int3store(buff, z_size);
192
180
    buff[3]= (unsigned char) net->pkt_nr++;
193
 
    if (net_write_buff(net, buff, NET_HEADER_SIZE) ||
194
 
        net_write_buff(net, packet, z_size))
 
181
    if (net_write_buff(net, buff, NET_HEADER_SIZE) || net_write_buff(net, packet, z_size))
195
182
      return 1;
196
183
    packet += z_size;
197
184
    len-=     z_size;
199
186
  /* Write last packet */
200
187
  int3store(buff,len);
201
188
  buff[3]= (unsigned char) net->pkt_nr++;
202
 
  if (net_write_buff(net, buff, NET_HEADER_SIZE))
203
 
    return 1;
204
 
  return net_write_buff(net,packet,len) ? 1 : 0;
 
189
  return net_write_buff(net, buff, NET_HEADER_SIZE) || net_write_buff(net, packet, len);
205
190
}
206
191
 
207
192
/**
231
216
   1    error
232
217
*/
233
218
 
234
 
bool
 
219
static bool
235
220
drizzleclient_net_write_command(NET *net,unsigned char command,
236
221
                  const unsigned char *header, size_t head_len,
237
222
                  const unsigned char *packet, size_t len)
264
249
  }
265
250
  int3store(buff,length);
266
251
  buff[3]= (unsigned char) net->pkt_nr++;
267
 
  return((net_write_buff(net, buff, header_size) ||
 
252
  return (net_write_buff(net, buff, header_size) ||
268
253
          (head_len && net_write_buff(net, header, head_len)) ||
269
 
          net_write_buff(net, packet, len) || drizzleclient_net_flush(net)) ? 1 : 0 );
 
254
          net_write_buff(net, packet, len) || net->flush());
270
255
}
271
256
 
272
257
/**
296
281
*/
297
282
 
298
283
static bool
299
 
net_write_buff(NET *net, const unsigned char *packet, uint32_t len)
 
284
net_write_buff(NET* net, const void* packet0, uint32_t len)
300
285
{
 
286
  const unsigned char* packet= reinterpret_cast<const unsigned char*>(packet0);
301
287
  uint32_t left_length;
302
288
  if (net->compress && net->max_packet > MAX_PACKET_LENGTH)
303
289
    left_length= MAX_PACKET_LENGTH - (net->write_pos - net->buff);
359
345
{
360
346
  /* Backup of the original SO_RCVTIMEO timeout */
361
347
 
362
 
  if (net->error == 2)
 
348
  if (net->error_ == 2)
363
349
    return(-1);                /* socket can't be used */
364
350
 
365
 
  net->reading_or_writing=2;
366
351
  if (net->compress)
367
352
  {
368
353
    const uint32_t header_length=NET_HEADER_SIZE+COMP_HEADER_SIZE;
426
411
        {
427
412
          if (net->vio->should_retry() && retry_count++ < net->retry_count)
428
413
            continue;
429
 
          net->error= 2;                     /* Close socket */
 
414
          net->error_= 2;                     /* Close socket */
430
415
          net->last_errno= ER_NET_PACKET_TOO_LARGE;
431
416
          my_error(ER_NET_PACKET_TOO_LARGE, MYF(0));
432
417
          goto end;
444
429
      {
445
430
        continue;
446
431
      }
447
 
      net->error= 2;                /* Close socket */
 
432
      net->error_= 2;                /* Close socket */
448
433
      net->last_errno= interrupted ? CR_NET_WRITE_INTERRUPTED : CR_NET_ERROR_ON_WRITE;
449
434
      break;
450
435
    }
457
442
end:
458
443
  if (net->compress)
459
444
    free((char*)packet);
460
 
  net->reading_or_writing=0;
461
445
 
462
446
  return (int) (pos != end);
463
447
}
475
459
static uint32_t
476
460
my_real_read(NET *net, size_t *complen)
477
461
{
478
 
  unsigned char *pos;
479
462
  size_t length= 0;
480
 
  uint32_t i,retry_count=0;
 
463
  uint32_t retry_count=0;
481
464
  size_t len=packet_error;
482
 
  uint32_t remain= (net->compress ? NET_HEADER_SIZE+COMP_HEADER_SIZE :
483
 
                    NET_HEADER_SIZE);
 
465
  uint32_t remain= net->compress ? NET_HEADER_SIZE+COMP_HEADER_SIZE : NET_HEADER_SIZE;
484
466
 
485
467
  *complen = 0;
486
468
 
487
 
  net->reading_or_writing= 1;
488
469
  /* Read timeout is set in drizzleclient_net_set_read_timeout */
489
470
 
490
 
  pos = net->buff + net->where_b;        /* net->packet -4 */
 
471
  unsigned char* pos = net->buff + net->where_b;        /* net->packet -4 */
491
472
 
492
 
  for (i= 0; i < 2 ; i++)
 
473
  for (uint32_t i= 0; i < 2 ; i++)
493
474
  {
494
475
    while (remain > 0)
495
476
    {
511
492
          continue;
512
493
        }
513
494
        len= packet_error;
514
 
        net->error= 2;                /* Close socket */
 
495
        net->error_= 2;                /* Close socket */
515
496
        net->last_errno= net->vio->was_interrupted() ? CR_NET_READ_INTERRUPTED : CR_NET_READ_ERROR;
516
497
        goto end;
517
498
      }
567
548
  }
568
549
 
569
550
end:
570
 
  net->reading_or_writing= 0;
571
 
 
572
 
  return(len);
 
551
  return len;
573
552
}
574
553
 
575
554
 
589
568
   net->read_pos points to the read data.
590
569
*/
591
570
 
592
 
uint32_t
 
571
static uint32_t
593
572
drizzleclient_net_read(NET *net)
594
573
{
595
574
  size_t len, complen;
718
697
 
719
698
          if (error != Z_OK)
720
699
          {
721
 
            net->error= 2;            /* caller will close socket */
 
700
            net->error_= 2;            /* caller will close socket */
722
701
            net->last_errno= CR_NET_UNCOMPRESS_ERROR;
723
702
          }
724
703
          else
747
726
  return len;
748
727
}
749
728
 
750
 
 
751
 
void drizzleclient_net_set_read_timeout(NET *net, uint32_t timeout)
752
 
{
753
 
  net->read_timeout= timeout;
754
 
#ifndef __sun
755
 
  if (net->vio)
756
 
    net->vio->timeout(0, timeout);
757
 
#endif
758
 
  return;
759
 
}
760
 
 
761
 
 
762
 
void drizzleclient_net_set_write_timeout(NET *net, uint32_t timeout)
763
 
{
764
 
  net->write_timeout= timeout;
765
 
#ifndef __sun
766
 
  if (net->vio)
767
 
    net->vio->timeout(1, timeout);
768
 
#endif
769
 
  return;
 
729
void NET::set_read_timeout(uint32_t timeout)
 
730
{
 
731
  read_timeout_= timeout;
 
732
#ifndef __sun
 
733
  if (vio)
 
734
    vio->timeout(0, timeout);
 
735
#endif
 
736
  return;
 
737
}
 
738
 
 
739
void NET::set_write_timeout(uint32_t timeout)
 
740
{
 
741
  write_timeout_= timeout;
 
742
#ifndef __sun
 
743
  if (vio)
 
744
    vio->timeout(1, timeout);
 
745
#endif
 
746
  return;
 
747
}
 
748
 
 
749
bool NET::write(const void* data, size_t size)
 
750
{
 
751
  return drizzleclient_net_write(this, data, size);
 
752
}
 
753
 
 
754
bool NET::write_command(unsigned char command,
 
755
  const unsigned char *header, size_t head_len,
 
756
  const unsigned char *packet, size_t len)
 
757
{
 
758
  return drizzleclient_net_write_command(this, command, header, head_len, packet, len);
 
759
}
 
760
 
 
761
uint32_t NET::read()
 
762
{
 
763
  return drizzleclient_net_read(this);
770
764
}
771
765
 
772
766
} /* namespace drizzle_plugin */