~percona-dev/percona-server/release-5.5.11-20.2-fix-bug-764138

« back to all changes in this revision

Viewing changes to HandlerSocket-Plugin-for-MySQL/libhsclient/string_buffer.hpp

  • Committer: Ignacio Nin
  • Date: 2011-03-13 17:18:23 UTC
  • mfrom: (33.3.17 release-5.5.8-20)
  • Revision ID: ignacio.nin@percona.com-20110313171823-m06xs104nekulywb
Merge changes from release-5.5.8-20 to 5.5.9

Merge changes from the release branch of 5.5.8 to 5.5.9. These include
the HandlerSocket and UDF directories and the building scripts.

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
 
 
2
// vim:sw=2:ai
 
3
 
 
4
/*
 
5
 * Copyright (C) 2010 DeNA Co.,Ltd.. All rights reserved.
 
6
 * See COPYRIGHT.txt for details.
 
7
 */
 
8
 
 
9
#ifndef DENA_STRING_BUFFER_HPP
 
10
#define DENA_STRING_BUFFER_HPP
 
11
 
 
12
#include <vector>
 
13
#include <stdlib.h>
 
14
#include <string.h>
 
15
 
 
16
#include "util.hpp"
 
17
#include "allocator.hpp"
 
18
#include "fatal.hpp"
 
19
 
 
20
namespace dena {
 
21
 
 
22
struct string_buffer : private noncopyable {
 
23
  string_buffer() : buffer(0), begin_offset(0), end_offset(0), alloc_size(0) { }
 
24
  ~string_buffer() {
 
25
    DENA_FREE(buffer);
 
26
  }
 
27
  const char *begin() const {
 
28
    return buffer + begin_offset;
 
29
  }
 
30
  const char *end() const {
 
31
    return buffer + end_offset;
 
32
  }
 
33
  char *begin() {
 
34
    return buffer + begin_offset;
 
35
  }
 
36
  char *end() {
 
37
    return buffer + end_offset;
 
38
  }
 
39
  size_t size() const {
 
40
    return end_offset - begin_offset;
 
41
  }
 
42
  void clear() {
 
43
    begin_offset = end_offset = 0;
 
44
  }
 
45
  void resize(size_t len) {
 
46
    if (size() < len) {
 
47
      reserve(len);
 
48
      memset(buffer + end_offset, 0, len - size());
 
49
    }
 
50
    end_offset = begin_offset + len;
 
51
  }
 
52
  void reserve(size_t len) {
 
53
    if (alloc_size >= begin_offset + len) {
 
54
      return;
 
55
    }
 
56
    size_t asz = alloc_size;
 
57
    while (asz < begin_offset + len) {
 
58
      if (asz == 0) {
 
59
        asz = 16;
 
60
      }
 
61
      const size_t asz_n = asz << 1;
 
62
      if (asz_n < asz) {
 
63
        fatal_abort("string_buffer::resize() overflow");
 
64
      }
 
65
      asz = asz_n;
 
66
    }
 
67
    void *const p = DENA_REALLOC(buffer, asz);
 
68
    if (p == 0) {
 
69
      fatal_abort("string_buffer::resize() realloc");
 
70
    }
 
71
    buffer = static_cast<char *>(p);
 
72
    alloc_size = asz;
 
73
  }
 
74
  void erase_front(size_t len) {
 
75
    if (len >= size()) {
 
76
      clear();
 
77
    } else {
 
78
      begin_offset += len;
 
79
    }
 
80
  }
 
81
  char *make_space(size_t len) {
 
82
    reserve(size() + len);
 
83
    return buffer + end_offset;
 
84
  }
 
85
  void space_wrote(size_t len) {
 
86
    len = std::min(len, alloc_size - end_offset);
 
87
    end_offset = std::min(end_offset + len, alloc_size);
 
88
  }
 
89
  template <size_t N>
 
90
  void append_literal(const char (& str)[N]) {
 
91
    append(str, str + N - 1);
 
92
  }
 
93
  void append(const char *start, const char *finish) {
 
94
    const size_t len = finish - start;
 
95
    reserve(size() + len);
 
96
    memcpy(buffer + end_offset, start, len);
 
97
    end_offset += len;
 
98
  }
 
99
  void append_2(const char *s1, const char *f1, const char *s2,
 
100
    const char *f2) {
 
101
    const size_t l1 = f1 - s1;
 
102
    const size_t l2 = f2 - s2;
 
103
    reserve(end_offset + l1 + l2);
 
104
    memcpy(buffer + end_offset, s1, l1);
 
105
    memcpy(buffer + end_offset + l1, s2, l2);
 
106
    end_offset += l1 + l2;
 
107
  }
 
108
 private:
 
109
  char *buffer;
 
110
  size_t begin_offset;
 
111
  size_t end_offset;
 
112
  size_t alloc_size;
 
113
};
 
114
 
 
115
};
 
116
 
 
117
#endif
 
118