| OLD | NEW |
| (Empty) |
| 1 """Class returned by TLSConnection.makefile().""" | |
| 2 | |
| 3 class FileObject: | |
| 4 """This class provides a file object interface to a | |
| 5 L{tlslite.TLSConnection.TLSConnection}. | |
| 6 | |
| 7 Call makefile() on a TLSConnection to create a FileObject instance. | |
| 8 | |
| 9 This class was copied, with minor modifications, from the | |
| 10 _fileobject class in socket.py. Note that fileno() is not | |
| 11 implemented.""" | |
| 12 | |
| 13 default_bufsize = 16384 #TREV: changed from 8192 | |
| 14 | |
| 15 def __init__(self, sock, mode='rb', bufsize=-1): | |
| 16 self._sock = sock | |
| 17 self.mode = mode # Not actually used in this version | |
| 18 if bufsize < 0: | |
| 19 bufsize = self.default_bufsize | |
| 20 self.bufsize = bufsize | |
| 21 self.softspace = False | |
| 22 if bufsize == 0: | |
| 23 self._rbufsize = 1 | |
| 24 elif bufsize == 1: | |
| 25 self._rbufsize = self.default_bufsize | |
| 26 else: | |
| 27 self._rbufsize = bufsize | |
| 28 self._wbufsize = bufsize | |
| 29 self._rbuf = "" # A string | |
| 30 self._wbuf = [] # A list of strings | |
| 31 | |
| 32 def _getclosed(self): | |
| 33 return self._sock is not None | |
| 34 closed = property(_getclosed, doc="True if the file is closed") | |
| 35 | |
| 36 def close(self): | |
| 37 try: | |
| 38 if self._sock: | |
| 39 for result in self._sock._decrefAsync(): #TREV | |
| 40 pass | |
| 41 finally: | |
| 42 self._sock = None | |
| 43 | |
| 44 def __del__(self): | |
| 45 try: | |
| 46 self.close() | |
| 47 except: | |
| 48 # close() may fail if __init__ didn't complete | |
| 49 pass | |
| 50 | |
| 51 def flush(self): | |
| 52 if self._wbuf: | |
| 53 buffer = "".join(self._wbuf) | |
| 54 self._wbuf = [] | |
| 55 self._sock.sendall(buffer) | |
| 56 | |
| 57 #def fileno(self): | |
| 58 # raise NotImplementedError() #TREV | |
| 59 | |
| 60 def write(self, data): | |
| 61 data = str(data) # XXX Should really reject non-string non-buffers | |
| 62 if not data: | |
| 63 return | |
| 64 self._wbuf.append(data) | |
| 65 if (self._wbufsize == 0 or | |
| 66 self._wbufsize == 1 and '\n' in data or | |
| 67 self._get_wbuf_len() >= self._wbufsize): | |
| 68 self.flush() | |
| 69 | |
| 70 def writelines(self, list): | |
| 71 # XXX We could do better here for very long lists | |
| 72 # XXX Should really reject non-string non-buffers | |
| 73 self._wbuf.extend(filter(None, map(str, list))) | |
| 74 if (self._wbufsize <= 1 or | |
| 75 self._get_wbuf_len() >= self._wbufsize): | |
| 76 self.flush() | |
| 77 | |
| 78 def _get_wbuf_len(self): | |
| 79 buf_len = 0 | |
| 80 for x in self._wbuf: | |
| 81 buf_len += len(x) | |
| 82 return buf_len | |
| 83 | |
| 84 def read(self, size=-1): | |
| 85 data = self._rbuf | |
| 86 if size < 0: | |
| 87 # Read until EOF | |
| 88 buffers = [] | |
| 89 if data: | |
| 90 buffers.append(data) | |
| 91 self._rbuf = "" | |
| 92 if self._rbufsize <= 1: | |
| 93 recv_size = self.default_bufsize | |
| 94 else: | |
| 95 recv_size = self._rbufsize | |
| 96 while True: | |
| 97 data = self._sock.recv(recv_size) | |
| 98 if not data: | |
| 99 break | |
| 100 buffers.append(data) | |
| 101 return "".join(buffers) | |
| 102 else: | |
| 103 # Read until size bytes or EOF seen, whichever comes first | |
| 104 buf_len = len(data) | |
| 105 if buf_len >= size: | |
| 106 self._rbuf = data[size:] | |
| 107 return data[:size] | |
| 108 buffers = [] | |
| 109 if data: | |
| 110 buffers.append(data) | |
| 111 self._rbuf = "" | |
| 112 while True: | |
| 113 left = size - buf_len | |
| 114 recv_size = max(self._rbufsize, left) | |
| 115 data = self._sock.recv(recv_size) | |
| 116 if not data: | |
| 117 break | |
| 118 buffers.append(data) | |
| 119 n = len(data) | |
| 120 if n >= left: | |
| 121 self._rbuf = data[left:] | |
| 122 buffers[-1] = data[:left] | |
| 123 break | |
| 124 buf_len += n | |
| 125 return "".join(buffers) | |
| 126 | |
| 127 def readline(self, size=-1): | |
| 128 data = self._rbuf | |
| 129 if size < 0: | |
| 130 # Read until \n or EOF, whichever comes first | |
| 131 if self._rbufsize <= 1: | |
| 132 # Speed up unbuffered case | |
| 133 assert data == "" | |
| 134 buffers = [] | |
| 135 recv = self._sock.recv | |
| 136 while data != "\n": | |
| 137 data = recv(1) | |
| 138 if not data: | |
| 139 break | |
| 140 buffers.append(data) | |
| 141 return "".join(buffers) | |
| 142 nl = data.find('\n') | |
| 143 if nl >= 0: | |
| 144 nl += 1 | |
| 145 self._rbuf = data[nl:] | |
| 146 return data[:nl] | |
| 147 buffers = [] | |
| 148 if data: | |
| 149 buffers.append(data) | |
| 150 self._rbuf = "" | |
| 151 while True: | |
| 152 data = self._sock.recv(self._rbufsize) | |
| 153 if not data: | |
| 154 break | |
| 155 buffers.append(data) | |
| 156 nl = data.find('\n') | |
| 157 if nl >= 0: | |
| 158 nl += 1 | |
| 159 self._rbuf = data[nl:] | |
| 160 buffers[-1] = data[:nl] | |
| 161 break | |
| 162 return "".join(buffers) | |
| 163 else: | |
| 164 # Read until size bytes or \n or EOF seen, whichever comes first | |
| 165 nl = data.find('\n', 0, size) | |
| 166 if nl >= 0: | |
| 167 nl += 1 | |
| 168 self._rbuf = data[nl:] | |
| 169 return data[:nl] | |
| 170 buf_len = len(data) | |
| 171 if buf_len >= size: | |
| 172 self._rbuf = data[size:] | |
| 173 return data[:size] | |
| 174 buffers = [] | |
| 175 if data: | |
| 176 buffers.append(data) | |
| 177 self._rbuf = "" | |
| 178 while True: | |
| 179 data = self._sock.recv(self._rbufsize) | |
| 180 if not data: | |
| 181 break | |
| 182 buffers.append(data) | |
| 183 left = size - buf_len | |
| 184 nl = data.find('\n', 0, left) | |
| 185 if nl >= 0: | |
| 186 nl += 1 | |
| 187 self._rbuf = data[nl:] | |
| 188 buffers[-1] = data[:nl] | |
| 189 break | |
| 190 n = len(data) | |
| 191 if n >= left: | |
| 192 self._rbuf = data[left:] | |
| 193 buffers[-1] = data[:left] | |
| 194 break | |
| 195 buf_len += n | |
| 196 return "".join(buffers) | |
| 197 | |
| 198 def readlines(self, sizehint=0): | |
| 199 total = 0 | |
| 200 list = [] | |
| 201 while True: | |
| 202 line = self.readline() | |
| 203 if not line: | |
| 204 break | |
| 205 list.append(line) | |
| 206 total += len(line) | |
| 207 if sizehint and total >= sizehint: | |
| 208 break | |
| 209 return list | |
| 210 | |
| 211 # Iterator protocols | |
| 212 | |
| 213 def __iter__(self): | |
| 214 return self | |
| 215 | |
| 216 def next(self): | |
| 217 line = self.readline() | |
| 218 if not line: | |
| 219 raise StopIteration | |
| 220 return line | |
| OLD | NEW |