1 // Copyright Joyent, Inc. and other Node contributors.
3 // Permission is hereby granted, free of charge, to any person obtaining a
4 // copy of this software and associated documentation files (the
5 // "Software"), to deal in the Software without restriction, including
6 // without limitation the rights to use, copy, modify, merge, publish,
7 // distribute, sublicense, and/or sell copies of the Software, and to permit
8 // persons to whom the Software is furnished to do so, subject to the
9 // following conditions:
11 // The above copyright notice and this permission notice shall be included
12 // in all copies or substantial portions of the Software.
14 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
15 // OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
16 // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN
17 // NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
18 // DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
19 // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE
20 // USE OR OTHER DEALINGS IN THE SOFTWARE.
22 var common = require('../common');
23 var assert = require('assert');
25 var Buffer = require('buffer').Buffer;
27 var b = Buffer(1024); // safe constructor
29 console.log('b.length == ' + b.length);
30 assert.strictEqual(1024, b.length);
33 assert.equal(b[0], 255);
35 for (var i = 0; i < 1024; i++) {
39 for (var i = 0; i < 1024; i++) {
40 assert.equal(i % 256, b[i]);
43 var c = new Buffer(512);
44 console.log('c.length == %d', c.length);
45 assert.strictEqual(512, c.length);
47 // copy 512 bytes, from 0 to 512.
48 var copied = b.copy(c, 0, 0, 512);
49 console.log('copied ' + copied + ' bytes from b into c');
50 assert.equal(512, copied);
51 for (var i = 0; i < c.length; i++) {
53 assert.equal(i % 256, c[i]);
57 // try to copy 513 bytes, and hope we don't overrun c, which is only 512 long
58 var copied = b.copy(c, 0, 0, 513);
59 console.log('copied ' + copied + ' bytes from b into c');
60 assert.strictEqual(512, copied);
61 for (var i = 0; i < c.length; i++) {
62 assert.equal(i % 256, c[i]);
65 // copy all of c back into b, without specifying sourceEnd
66 var copied = c.copy(b, 0, 0);
67 console.log('copied ' + copied + ' bytes from c back into b');
68 assert.strictEqual(512, copied);
69 for (var i = 0; i < b.length; i++) {
70 assert.equal(i % 256, b[i]);
73 // copy 768 bytes from b into b
74 var copied = b.copy(b, 0, 256, 1024);
75 console.log('copied ' + copied + ' bytes from b into c');
76 assert.strictEqual(768, copied);
77 for (var i = 0; i < c.length; i++) {
78 assert.equal(i % 256, c[i]);
81 var caught_error = null;
83 // try to copy from before the beginning of b
86 var copied = b.copy(c, 0, 100, 10);
90 assert.strictEqual('sourceEnd < sourceStart', caught_error.message);
92 // try to copy to before the beginning of c
95 var copied = b.copy(c, -1, 0, 10);
99 assert.strictEqual('targetStart out of bounds', caught_error.message);
101 // try to copy to after the end of c
104 var copied = b.copy(c, 512, 0, 10);
108 assert.strictEqual('targetStart out of bounds', caught_error.message);
110 // try to copy starting before the beginning of b
113 var copied = b.copy(c, 0, -1, 1);
117 assert.strictEqual('sourceStart out of bounds', caught_error.message);
119 // try to copy starting after the end of b
122 var copied = b.copy(c, 0, 1024, 1025);
126 assert.strictEqual('sourceStart out of bounds', caught_error.message);
128 // a too-low sourceEnd will get caught by earlier checks
130 // try to copy ending after the end of b
132 var copied = b.copy(c, 0, 1023, 1025);
136 assert.strictEqual('sourceEnd out of bounds', caught_error.message);
138 // try to create 0-length buffers
140 new Buffer('', 'ascii');
141 new Buffer('', 'binary');
144 // try to write a 0-length string beyond the end of b
148 // try to copy 0 bytes worth of data into an empty buffer
149 b.copy(new Buffer(0), 0, 0, 0);
151 // try to copy 0 bytes past the end of the target buffer
152 b.copy(new Buffer(0), 1, 1, 1);
153 b.copy(new Buffer(1), 1, 1, 1);
155 // try to copy 0 bytes from past the end of the source buffer
156 b.copy(new Buffer(1), 0, 2048, 2048);
158 // try to toString() a 0-length slice of a buffer, both within and without the
159 // valid buffer range
160 assert.equal(new Buffer('abc').toString('ascii', 0, 0), '');
161 assert.equal(new Buffer('abc').toString('ascii', -100, -100), '');
162 assert.equal(new Buffer('abc').toString('ascii', 100, 100), '');
164 // try toString() with a object as a encoding
165 assert.equal(new Buffer('abc').toString({toString: function() {
169 // testing for smart defaults and ability to pass string values as offset
170 var writeTest = new Buffer('abcdes');
171 writeTest.write('n', 'ascii');
172 writeTest.write('o', 'ascii', '1');
173 writeTest.write('d', '2', 'ascii');
174 writeTest.write('e', 3, 'ascii');
175 writeTest.write('j', 'ascii', 4);
176 assert.equal(writeTest.toString(), 'nodejs');
178 var asciiString = 'hello world';
180 for (var j = 0; j < 500; j++) {
182 for (var i = 0; i < asciiString.length; i++) {
183 b[i] = asciiString.charCodeAt(i);
185 var asciiSlice = b.toString('ascii', 0, asciiString.length);
186 assert.equal(asciiString, asciiSlice);
188 var written = b.write(asciiString, offset, 'ascii');
189 assert.equal(asciiString.length, written);
190 var asciiSlice = b.toString('ascii', offset, offset + asciiString.length);
191 assert.equal(asciiString, asciiSlice);
193 var sliceA = b.slice(offset, offset + asciiString.length);
194 var sliceB = b.slice(offset, offset + asciiString.length);
195 for (var i = 0; i < asciiString.length; i++) {
196 assert.equal(sliceA[i], sliceB[i]);
199 // TODO utf8 slice tests
203 for (var j = 0; j < 100; j++) {
204 var slice = b.slice(100, 150);
205 assert.equal(50, slice.length);
206 for (var i = 0; i < 50; i++) {
207 assert.equal(b[100 + i], slice[i]);
213 // Bug regression test
214 var testValue = '\u00F6\u65E5\u672C\u8A9E'; // ö日本語
215 var buffer = new Buffer(32);
216 var size = buffer.write(testValue, 0, 'utf8');
217 console.log('bytes written to buffer: ' + size);
218 var slice = buffer.toString('utf8', 0, size);
219 assert.equal(slice, testValue);
223 var a = new Buffer(8);
224 for (var i = 0; i < 8; i++) a[i] = i;
225 var b = a.slice(4, 8);
226 assert.equal(4, b[0]);
227 assert.equal(5, b[1]);
228 assert.equal(6, b[2]);
229 assert.equal(7, b[3]);
230 var c = b.slice(2, 4);
231 assert.equal(6, c[0]);
232 assert.equal(7, c[1]);
235 var d = new Buffer([23, 42, 255]);
236 assert.equal(d.length, 3);
237 assert.equal(d[0], 23);
238 assert.equal(d[1], 42);
239 assert.equal(d[2], 255);
240 assert.deepEqual(d, new Buffer(d));
242 var e = new Buffer('über');
243 console.error('uber: \'%s\'', e.toString());
244 assert.deepEqual(e, new Buffer([195, 188, 98, 101, 114]));
246 var f = new Buffer('über', 'ascii');
247 console.error('f.length: %d (should be 4)', f.length);
248 assert.deepEqual(f, new Buffer([252, 98, 101, 114]));
250 var f = new Buffer('über', 'ucs2');
251 console.error('f.length: %d (should be 8)', f.length);
252 assert.deepEqual(f, new Buffer([252, 0, 98, 0, 101, 0, 114, 0]));
254 var f = new Buffer('привет', 'ucs2');
255 console.error('f.length: %d (should be 12)', f.length);
256 assert.deepEqual(f, new Buffer([63, 4, 64, 4, 56, 4, 50, 4, 53, 4, 66, 4]));
257 assert.equal(f.toString('ucs2'), 'привет');
260 var arrayIsh = {0: 0, 1: 1, 2: 2, 3: 3, length: 4};
261 var g = new Buffer(arrayIsh);
262 assert.deepEqual(g, new Buffer([0, 1, 2, 3]));
263 var strArrayIsh = {0: '0', 1: '1', 2: '2', 3: '3', length: 4};
264 g = new Buffer(strArrayIsh);
265 assert.deepEqual(g, new Buffer([0, 1, 2, 3]));
269 // Test toString('base64')
271 assert.equal('TWFu', (new Buffer('Man')).toString('base64'));
273 var quote = 'Man is distinguished, not only by his reason, but by this ' +
274 'singular passion from other animals, which is a lust ' +
275 'of the mind, that by a perseverance of delight in the continued ' +
276 'and indefatigable generation of knowledge, exceeds the short ' +
277 'vehemence of any carnal pleasure.';
278 var expected = 'TWFuIGlzIGRpc3Rpbmd1aXNoZWQsIG5vdCBvbmx5IGJ5IGhpcyByZWFzb24s' +
279 'IGJ1dCBieSB0aGlzIHNpbmd1bGFyIHBhc3Npb24gZnJvbSBvdGhlciBhbmltY' +
280 'WxzLCB3aGljaCBpcyBhIGx1c3Qgb2YgdGhlIG1pbmQsIHRoYXQgYnkgYSBwZX' +
281 'JzZXZlcmFuY2Ugb2YgZGVsaWdodCBpbiB0aGUgY29udGludWVkIGFuZCBpbmR' +
282 'lZmF0aWdhYmxlIGdlbmVyYXRpb24gb2Yga25vd2xlZGdlLCBleGNlZWRzIHRo' +
283 'ZSBzaG9ydCB2ZWhlbWVuY2Ugb2YgYW55IGNhcm5hbCBwbGVhc3VyZS4=';
284 assert.equal(expected, (new Buffer(quote)).toString('base64'));
287 b = new Buffer(1024);
288 var bytesWritten = b.write(expected, 0, 'base64');
289 assert.equal(quote.length, bytesWritten);
290 assert.equal(quote, b.toString('ascii', 0, quote.length));
292 // check that the base64 decoder ignores whitespace
293 var expectedWhite = expected.slice(0, 60) + ' \n' +
294 expected.slice(60, 120) + ' \n' +
295 expected.slice(120, 180) + ' \n' +
296 expected.slice(180, 240) + ' \n' +
297 expected.slice(240, 300) + '\n' +
298 expected.slice(300, 360) + '\n';
299 b = new Buffer(1024);
300 bytesWritten = b.write(expectedWhite, 0, 'base64');
301 assert.equal(quote.length, bytesWritten);
302 assert.equal(quote, b.toString('ascii', 0, quote.length));
304 // check that the base64 decoder on the constructor works
305 // even in the presence of whitespace.
306 b = new Buffer(expectedWhite, 'base64');
307 assert.equal(quote.length, b.length);
308 assert.equal(quote, b.toString('ascii', 0, quote.length));
310 // check that the base64 decoder ignores illegal chars
311 var expectedIllegal = expected.slice(0, 60) + ' \x80' +
312 expected.slice(60, 120) + ' \xff' +
313 expected.slice(120, 180) + ' \x00' +
314 expected.slice(180, 240) + ' \x98' +
315 expected.slice(240, 300) + '\x03' +
316 expected.slice(300, 360);
317 b = new Buffer(expectedIllegal, 'base64');
318 assert.equal(quote.length, b.length);
319 assert.equal(quote, b.toString('ascii', 0, quote.length));
322 assert.equal(new Buffer('', 'base64').toString(), '');
323 assert.equal(new Buffer('K', 'base64').toString(), '');
325 // multiple-of-4 with padding
326 assert.equal(new Buffer('Kg==', 'base64').toString(), '*');
327 assert.equal(new Buffer('Kio=', 'base64').toString(), '**');
328 assert.equal(new Buffer('Kioq', 'base64').toString(), '***');
329 assert.equal(new Buffer('KioqKg==', 'base64').toString(), '****');
330 assert.equal(new Buffer('KioqKio=', 'base64').toString(), '*****');
331 assert.equal(new Buffer('KioqKioq', 'base64').toString(), '******');
332 assert.equal(new Buffer('KioqKioqKg==', 'base64').toString(), '*******');
333 assert.equal(new Buffer('KioqKioqKio=', 'base64').toString(), '********');
334 assert.equal(new Buffer('KioqKioqKioq', 'base64').toString(), '*********');
335 assert.equal(new Buffer('KioqKioqKioqKg==', 'base64').toString(),
337 assert.equal(new Buffer('KioqKioqKioqKio=', 'base64').toString(),
339 assert.equal(new Buffer('KioqKioqKioqKioq', 'base64').toString(),
341 assert.equal(new Buffer('KioqKioqKioqKioqKg==', 'base64').toString(),
343 assert.equal(new Buffer('KioqKioqKioqKioqKio=', 'base64').toString(),
345 assert.equal(new Buffer('KioqKioqKioqKioqKioq', 'base64').toString(),
347 assert.equal(new Buffer('KioqKioqKioqKioqKioqKg==', 'base64').toString(),
349 assert.equal(new Buffer('KioqKioqKioqKioqKioqKio=', 'base64').toString(),
350 '*****************');
351 assert.equal(new Buffer('KioqKioqKioqKioqKioqKioq', 'base64').toString(),
352 '******************');
353 assert.equal(new Buffer('KioqKioqKioqKioqKioqKioqKg==', 'base64').toString(),
354 '*******************');
355 assert.equal(new Buffer('KioqKioqKioqKioqKioqKioqKio=', 'base64').toString(),
356 '********************');
358 // no padding, not a multiple of 4
359 assert.equal(new Buffer('Kg', 'base64').toString(), '*');
360 assert.equal(new Buffer('Kio', 'base64').toString(), '**');
361 assert.equal(new Buffer('KioqKg', 'base64').toString(), '****');
362 assert.equal(new Buffer('KioqKio', 'base64').toString(), '*****');
363 assert.equal(new Buffer('KioqKioqKg', 'base64').toString(), '*******');
364 assert.equal(new Buffer('KioqKioqKio', 'base64').toString(), '********');
365 assert.equal(new Buffer('KioqKioqKioqKg', 'base64').toString(), '**********');
366 assert.equal(new Buffer('KioqKioqKioqKio', 'base64').toString(), '***********');
367 assert.equal(new Buffer('KioqKioqKioqKioqKg', 'base64').toString(),
369 assert.equal(new Buffer('KioqKioqKioqKioqKio', 'base64').toString(),
371 assert.equal(new Buffer('KioqKioqKioqKioqKioqKg', 'base64').toString(),
373 assert.equal(new Buffer('KioqKioqKioqKioqKioqKio', 'base64').toString(),
374 '*****************');
375 assert.equal(new Buffer('KioqKioqKioqKioqKioqKioqKg', 'base64').toString(),
376 '*******************');
377 assert.equal(new Buffer('KioqKioqKioqKioqKioqKioqKio', 'base64').toString(),
378 '********************');
380 // handle padding graciously, multiple-of-4 or not
381 assert.equal(new Buffer('72INjkR5fchcxk9+VgdGPFJDxUBFR5/rMFsghgxADiw==',
382 'base64').length, 32);
383 assert.equal(new Buffer('72INjkR5fchcxk9+VgdGPFJDxUBFR5/rMFsghgxADiw=',
384 'base64').length, 32);
385 assert.equal(new Buffer('72INjkR5fchcxk9+VgdGPFJDxUBFR5/rMFsghgxADiw',
386 'base64').length, 32);
387 assert.equal(new Buffer('w69jACy6BgZmaFvv96HG6MYksWytuZu3T1FvGnulPg==',
388 'base64').length, 31);
389 assert.equal(new Buffer('w69jACy6BgZmaFvv96HG6MYksWytuZu3T1FvGnulPg=',
390 'base64').length, 31);
391 assert.equal(new Buffer('w69jACy6BgZmaFvv96HG6MYksWytuZu3T1FvGnulPg',
392 'base64').length, 31);
394 // This string encodes single '.' character in UTF-16
395 var dot = new Buffer('//4uAA==', 'base64');
396 assert.equal(dot[0], 0xff);
397 assert.equal(dot[1], 0xfe);
398 assert.equal(dot[2], 0x2e);
399 assert.equal(dot[3], 0x00);
400 assert.equal(dot.toString('base64'), '//4uAA==');
403 // Creating buffers larger than pool size.
404 var l = Buffer.poolSize + 5;
406 for (i = 0; i < l; i++) {
410 var b = new Buffer(s);
412 for (i = 0; i < l; i++) {
413 assert.equal('h'.charCodeAt(0), b[i]);
416 var sb = b.toString();
417 assert.equal(sb.length, s.length);
421 // Single argument slice
422 b = new Buffer('abcde');
423 assert.equal('bcde', b.slice(1).toString());
426 assert.equal(14, Buffer.byteLength('Il était tué'));
427 assert.equal(14, Buffer.byteLength('Il était tué', 'utf8'));
428 assert.equal(24, Buffer.byteLength('Il était tué', 'ucs2'));
429 assert.equal(12, Buffer.byteLength('Il était tué', 'ascii'));
430 assert.equal(12, Buffer.byteLength('Il était tué', 'binary'));
432 // slice(0,0).length === 0
433 assert.equal(0, Buffer('hello').slice(0, 0).length);
436 console.log('Create hex string from buffer');
437 var hexb = new Buffer(256);
438 for (var i = 0; i < 256; i ++) {
441 var hexStr = hexb.toString('hex');
443 '000102030405060708090a0b0c0d0e0f'+
444 '101112131415161718191a1b1c1d1e1f'+
445 '202122232425262728292a2b2c2d2e2f'+
446 '303132333435363738393a3b3c3d3e3f'+
447 '404142434445464748494a4b4c4d4e4f'+
448 '505152535455565758595a5b5c5d5e5f'+
449 '606162636465666768696a6b6c6d6e6f'+
450 '707172737475767778797a7b7c7d7e7f'+
451 '808182838485868788898a8b8c8d8e8f'+
452 '909192939495969798999a9b9c9d9e9f'+
453 'a0a1a2a3a4a5a6a7a8a9aaabacadaeaf'+
454 'b0b1b2b3b4b5b6b7b8b9babbbcbdbebf'+
455 'c0c1c2c3c4c5c6c7c8c9cacbcccdcecf'+
456 'd0d1d2d3d4d5d6d7d8d9dadbdcdddedf'+
457 'e0e1e2e3e4e5e6e7e8e9eaebecedeeef'+
458 'f0f1f2f3f4f5f6f7f8f9fafbfcfdfeff');
460 console.log('Create buffer from hex string');
461 var hexb2 = new Buffer(hexStr, 'hex');
462 for (var i = 0; i < 256; i ++) {
463 assert.equal(hexb2[i], hexb[i]);
466 // test an invalid slice end.
467 console.log('Try to slice off the end of the buffer');
468 var b = new Buffer([1,2,3,4,5]);
469 var b2 = b.toString('hex', 1, 10000);
470 var b3 = b.toString('hex', 1, 5);
471 var b4 = b.toString('hex', 1);
472 assert.equal(b2, b3);
473 assert.equal(b2, b4);