View Javadoc
1   /*
2    * Copyright 2013 The Netty Project
3    *
4    * The Netty Project licenses this file to you under the Apache License,
5    * version 2.0 (the "License"); you may not use this file except in compliance
6    * with the License. You may obtain a copy of the License at:
7    *
8    *   http://www.apache.org/licenses/LICENSE-2.0
9    *
10   * Unless required by applicable law or agreed to in writing, software
11   * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
12   * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
13   * License for the specific language governing permissions and limitations
14   * under the License.
15   */
16  
17  package io.netty.buffer;
18  
19  import io.netty.util.ResourceLeakDetector;
20  import io.netty.util.ResourceLeakTracker;
21  import io.netty.util.internal.SystemPropertyUtil;
22  import io.netty.util.internal.logging.InternalLogger;
23  import io.netty.util.internal.logging.InternalLoggerFactory;
24  
25  import java.io.IOException;
26  import java.io.InputStream;
27  import java.io.OutputStream;
28  import java.nio.ByteBuffer;
29  import java.nio.ByteOrder;
30  import java.nio.channels.GatheringByteChannel;
31  import java.nio.channels.ScatteringByteChannel;
32  import java.nio.charset.Charset;
33  
34  final class AdvancedLeakAwareByteBuf extends SimpleLeakAwareByteBuf {
35  
36      private static final String PROP_ACQUIRE_AND_RELEASE_ONLY = "io.netty.leakDetection.acquireAndReleaseOnly";
37      private static final boolean ACQUIRE_AND_RELEASE_ONLY;
38  
39      private static final InternalLogger logger = InternalLoggerFactory.getInstance(AdvancedLeakAwareByteBuf.class);
40  
41      static {
42          ACQUIRE_AND_RELEASE_ONLY = SystemPropertyUtil.getBoolean(PROP_ACQUIRE_AND_RELEASE_ONLY, false);
43  
44          if (logger.isDebugEnabled()) {
45              logger.debug("-D{}: {}", PROP_ACQUIRE_AND_RELEASE_ONLY, ACQUIRE_AND_RELEASE_ONLY);
46          }
47  
48          ResourceLeakDetector.addExclusions(
49                  AdvancedLeakAwareByteBuf.class, "recordLeakNonRefCountingOperation");
50      }
51  
52      AdvancedLeakAwareByteBuf(ByteBuf buf, ResourceLeakTracker<ByteBuf> leak) {
53          super(buf, leak);
54      }
55  
56      AdvancedLeakAwareByteBuf(ByteBuf wrapped, ByteBuf trackedByteBuf, ResourceLeakTracker<ByteBuf> leak) {
57          super(wrapped, trackedByteBuf, leak);
58      }
59  
60      static void recordLeakNonRefCountingOperation(ResourceLeakTracker<ByteBuf> leak) {
61          if (!ACQUIRE_AND_RELEASE_ONLY) {
62              leak.record();
63          }
64      }
65  
66      @Override
67      public ByteBuf order(ByteOrder endianness) {
68          recordLeakNonRefCountingOperation(leak);
69          return super.order(endianness);
70      }
71  
72      @Override
73      public ByteBuf slice() {
74          recordLeakNonRefCountingOperation(leak);
75          return super.slice();
76      }
77  
78      @Override
79      public ByteBuf slice(int index, int length) {
80          recordLeakNonRefCountingOperation(leak);
81          return super.slice(index, length);
82      }
83  
84      @Override
85      public ByteBuf duplicate() {
86          recordLeakNonRefCountingOperation(leak);
87          return super.duplicate();
88      }
89  
90      @Override
91      public ByteBuf readSlice(int length) {
92          recordLeakNonRefCountingOperation(leak);
93          return super.readSlice(length);
94      }
95  
96      @Override
97      public ByteBuf discardReadBytes() {
98          recordLeakNonRefCountingOperation(leak);
99          return super.discardReadBytes();
100     }
101 
102     @Override
103     public ByteBuf discardSomeReadBytes() {
104         recordLeakNonRefCountingOperation(leak);
105         return super.discardSomeReadBytes();
106     }
107 
108     @Override
109     public ByteBuf ensureWritable(int minWritableBytes) {
110         recordLeakNonRefCountingOperation(leak);
111         return super.ensureWritable(minWritableBytes);
112     }
113 
114     @Override
115     public int ensureWritable(int minWritableBytes, boolean force) {
116         recordLeakNonRefCountingOperation(leak);
117         return super.ensureWritable(minWritableBytes, force);
118     }
119 
120     @Override
121     public boolean getBoolean(int index) {
122         recordLeakNonRefCountingOperation(leak);
123         return super.getBoolean(index);
124     }
125 
126     @Override
127     public byte getByte(int index) {
128         recordLeakNonRefCountingOperation(leak);
129         return super.getByte(index);
130     }
131 
132     @Override
133     public short getUnsignedByte(int index) {
134         recordLeakNonRefCountingOperation(leak);
135         return super.getUnsignedByte(index);
136     }
137 
138     @Override
139     public short getShort(int index) {
140         recordLeakNonRefCountingOperation(leak);
141         return super.getShort(index);
142     }
143 
144     @Override
145     public int getUnsignedShort(int index) {
146         recordLeakNonRefCountingOperation(leak);
147         return super.getUnsignedShort(index);
148     }
149 
150     @Override
151     public int getMedium(int index) {
152         recordLeakNonRefCountingOperation(leak);
153         return super.getMedium(index);
154     }
155 
156     @Override
157     public int getUnsignedMedium(int index) {
158         recordLeakNonRefCountingOperation(leak);
159         return super.getUnsignedMedium(index);
160     }
161 
162     @Override
163     public int getInt(int index) {
164         recordLeakNonRefCountingOperation(leak);
165         return super.getInt(index);
166     }
167 
168     @Override
169     public long getUnsignedInt(int index) {
170         recordLeakNonRefCountingOperation(leak);
171         return super.getUnsignedInt(index);
172     }
173 
174     @Override
175     public long getLong(int index) {
176         recordLeakNonRefCountingOperation(leak);
177         return super.getLong(index);
178     }
179 
180     @Override
181     public char getChar(int index) {
182         recordLeakNonRefCountingOperation(leak);
183         return super.getChar(index);
184     }
185 
186     @Override
187     public float getFloat(int index) {
188         recordLeakNonRefCountingOperation(leak);
189         return super.getFloat(index);
190     }
191 
192     @Override
193     public double getDouble(int index) {
194         recordLeakNonRefCountingOperation(leak);
195         return super.getDouble(index);
196     }
197 
198     @Override
199     public ByteBuf getBytes(int index, ByteBuf dst) {
200         recordLeakNonRefCountingOperation(leak);
201         return super.getBytes(index, dst);
202     }
203 
204     @Override
205     public ByteBuf getBytes(int index, ByteBuf dst, int length) {
206         recordLeakNonRefCountingOperation(leak);
207         return super.getBytes(index, dst, length);
208     }
209 
210     @Override
211     public ByteBuf getBytes(int index, ByteBuf dst, int dstIndex, int length) {
212         recordLeakNonRefCountingOperation(leak);
213         return super.getBytes(index, dst, dstIndex, length);
214     }
215 
216     @Override
217     public ByteBuf getBytes(int index, byte[] dst) {
218         recordLeakNonRefCountingOperation(leak);
219         return super.getBytes(index, dst);
220     }
221 
222     @Override
223     public ByteBuf getBytes(int index, byte[] dst, int dstIndex, int length) {
224         recordLeakNonRefCountingOperation(leak);
225         return super.getBytes(index, dst, dstIndex, length);
226     }
227 
228     @Override
229     public ByteBuf getBytes(int index, ByteBuffer dst) {
230         recordLeakNonRefCountingOperation(leak);
231         return super.getBytes(index, dst);
232     }
233 
234     @Override
235     public ByteBuf getBytes(int index, OutputStream out, int length) throws IOException {
236         recordLeakNonRefCountingOperation(leak);
237         return super.getBytes(index, out, length);
238     }
239 
240     @Override
241     public int getBytes(int index, GatheringByteChannel out, int length) throws IOException {
242         recordLeakNonRefCountingOperation(leak);
243         return super.getBytes(index, out, length);
244     }
245 
246     @Override
247     public ByteBuf setBoolean(int index, boolean value) {
248         recordLeakNonRefCountingOperation(leak);
249         return super.setBoolean(index, value);
250     }
251 
252     @Override
253     public ByteBuf setByte(int index, int value) {
254         recordLeakNonRefCountingOperation(leak);
255         return super.setByte(index, value);
256     }
257 
258     @Override
259     public ByteBuf setShort(int index, int value) {
260         recordLeakNonRefCountingOperation(leak);
261         return super.setShort(index, value);
262     }
263 
264     @Override
265     public ByteBuf setMedium(int index, int value) {
266         recordLeakNonRefCountingOperation(leak);
267         return super.setMedium(index, value);
268     }
269 
270     @Override
271     public ByteBuf setInt(int index, int value) {
272         recordLeakNonRefCountingOperation(leak);
273         return super.setInt(index, value);
274     }
275 
276     @Override
277     public ByteBuf setLong(int index, long value) {
278         recordLeakNonRefCountingOperation(leak);
279         return super.setLong(index, value);
280     }
281 
282     @Override
283     public ByteBuf setChar(int index, int value) {
284         recordLeakNonRefCountingOperation(leak);
285         return super.setChar(index, value);
286     }
287 
288     @Override
289     public ByteBuf setFloat(int index, float value) {
290         recordLeakNonRefCountingOperation(leak);
291         return super.setFloat(index, value);
292     }
293 
294     @Override
295     public ByteBuf setDouble(int index, double value) {
296         recordLeakNonRefCountingOperation(leak);
297         return super.setDouble(index, value);
298     }
299 
300     @Override
301     public ByteBuf setBytes(int index, ByteBuf src) {
302         recordLeakNonRefCountingOperation(leak);
303         return super.setBytes(index, src);
304     }
305 
306     @Override
307     public ByteBuf setBytes(int index, ByteBuf src, int length) {
308         recordLeakNonRefCountingOperation(leak);
309         return super.setBytes(index, src, length);
310     }
311 
312     @Override
313     public ByteBuf setBytes(int index, ByteBuf src, int srcIndex, int length) {
314         recordLeakNonRefCountingOperation(leak);
315         return super.setBytes(index, src, srcIndex, length);
316     }
317 
318     @Override
319     public ByteBuf setBytes(int index, byte[] src) {
320         recordLeakNonRefCountingOperation(leak);
321         return super.setBytes(index, src);
322     }
323 
324     @Override
325     public ByteBuf setBytes(int index, byte[] src, int srcIndex, int length) {
326         recordLeakNonRefCountingOperation(leak);
327         return super.setBytes(index, src, srcIndex, length);
328     }
329 
330     @Override
331     public ByteBuf setBytes(int index, ByteBuffer src) {
332         recordLeakNonRefCountingOperation(leak);
333         return super.setBytes(index, src);
334     }
335 
336     @Override
337     public int setBytes(int index, InputStream in, int length) throws IOException {
338         recordLeakNonRefCountingOperation(leak);
339         return super.setBytes(index, in, length);
340     }
341 
342     @Override
343     public int setBytes(int index, ScatteringByteChannel in, int length) throws IOException {
344         recordLeakNonRefCountingOperation(leak);
345         return super.setBytes(index, in, length);
346     }
347 
348     @Override
349     public ByteBuf setZero(int index, int length) {
350         recordLeakNonRefCountingOperation(leak);
351         return super.setZero(index, length);
352     }
353 
354     @Override
355     public boolean readBoolean() {
356         recordLeakNonRefCountingOperation(leak);
357         return super.readBoolean();
358     }
359 
360     @Override
361     public byte readByte() {
362         recordLeakNonRefCountingOperation(leak);
363         return super.readByte();
364     }
365 
366     @Override
367     public short readUnsignedByte() {
368         recordLeakNonRefCountingOperation(leak);
369         return super.readUnsignedByte();
370     }
371 
372     @Override
373     public short readShort() {
374         recordLeakNonRefCountingOperation(leak);
375         return super.readShort();
376     }
377 
378     @Override
379     public int readUnsignedShort() {
380         recordLeakNonRefCountingOperation(leak);
381         return super.readUnsignedShort();
382     }
383 
384     @Override
385     public int readMedium() {
386         recordLeakNonRefCountingOperation(leak);
387         return super.readMedium();
388     }
389 
390     @Override
391     public int readUnsignedMedium() {
392         recordLeakNonRefCountingOperation(leak);
393         return super.readUnsignedMedium();
394     }
395 
396     @Override
397     public int readInt() {
398         recordLeakNonRefCountingOperation(leak);
399         return super.readInt();
400     }
401 
402     @Override
403     public long readUnsignedInt() {
404         recordLeakNonRefCountingOperation(leak);
405         return super.readUnsignedInt();
406     }
407 
408     @Override
409     public long readLong() {
410         recordLeakNonRefCountingOperation(leak);
411         return super.readLong();
412     }
413 
414     @Override
415     public char readChar() {
416         recordLeakNonRefCountingOperation(leak);
417         return super.readChar();
418     }
419 
420     @Override
421     public float readFloat() {
422         recordLeakNonRefCountingOperation(leak);
423         return super.readFloat();
424     }
425 
426     @Override
427     public double readDouble() {
428         recordLeakNonRefCountingOperation(leak);
429         return super.readDouble();
430     }
431 
432     @Override
433     public ByteBuf readBytes(int length) {
434         recordLeakNonRefCountingOperation(leak);
435         return super.readBytes(length);
436     }
437 
438     @Override
439     public ByteBuf readBytes(ByteBuf dst) {
440         recordLeakNonRefCountingOperation(leak);
441         return super.readBytes(dst);
442     }
443 
444     @Override
445     public ByteBuf readBytes(ByteBuf dst, int length) {
446         recordLeakNonRefCountingOperation(leak);
447         return super.readBytes(dst, length);
448     }
449 
450     @Override
451     public ByteBuf readBytes(ByteBuf dst, int dstIndex, int length) {
452         recordLeakNonRefCountingOperation(leak);
453         return super.readBytes(dst, dstIndex, length);
454     }
455 
456     @Override
457     public ByteBuf readBytes(byte[] dst) {
458         recordLeakNonRefCountingOperation(leak);
459         return super.readBytes(dst);
460     }
461 
462     @Override
463     public ByteBuf readBytes(byte[] dst, int dstIndex, int length) {
464         recordLeakNonRefCountingOperation(leak);
465         return super.readBytes(dst, dstIndex, length);
466     }
467 
468     @Override
469     public ByteBuf readBytes(ByteBuffer dst) {
470         recordLeakNonRefCountingOperation(leak);
471         return super.readBytes(dst);
472     }
473 
474     @Override
475     public ByteBuf readBytes(OutputStream out, int length) throws IOException {
476         recordLeakNonRefCountingOperation(leak);
477         return super.readBytes(out, length);
478     }
479 
480     @Override
481     public int readBytes(GatheringByteChannel out, int length) throws IOException {
482         recordLeakNonRefCountingOperation(leak);
483         return super.readBytes(out, length);
484     }
485 
486     @Override
487     public ByteBuf skipBytes(int length) {
488         recordLeakNonRefCountingOperation(leak);
489         return super.skipBytes(length);
490     }
491 
492     @Override
493     public ByteBuf writeBoolean(boolean value) {
494         recordLeakNonRefCountingOperation(leak);
495         return super.writeBoolean(value);
496     }
497 
498     @Override
499     public ByteBuf writeByte(int value) {
500         recordLeakNonRefCountingOperation(leak);
501         return super.writeByte(value);
502     }
503 
504     @Override
505     public ByteBuf writeShort(int value) {
506         recordLeakNonRefCountingOperation(leak);
507         return super.writeShort(value);
508     }
509 
510     @Override
511     public ByteBuf writeMedium(int value) {
512         recordLeakNonRefCountingOperation(leak);
513         return super.writeMedium(value);
514     }
515 
516     @Override
517     public ByteBuf writeInt(int value) {
518         recordLeakNonRefCountingOperation(leak);
519         return super.writeInt(value);
520     }
521 
522     @Override
523     public ByteBuf writeLong(long value) {
524         recordLeakNonRefCountingOperation(leak);
525         return super.writeLong(value);
526     }
527 
528     @Override
529     public ByteBuf writeChar(int value) {
530         recordLeakNonRefCountingOperation(leak);
531         return super.writeChar(value);
532     }
533 
534     @Override
535     public ByteBuf writeFloat(float value) {
536         recordLeakNonRefCountingOperation(leak);
537         return super.writeFloat(value);
538     }
539 
540     @Override
541     public ByteBuf writeDouble(double value) {
542         recordLeakNonRefCountingOperation(leak);
543         return super.writeDouble(value);
544     }
545 
546     @Override
547     public ByteBuf writeBytes(ByteBuf src) {
548         recordLeakNonRefCountingOperation(leak);
549         return super.writeBytes(src);
550     }
551 
552     @Override
553     public ByteBuf writeBytes(ByteBuf src, int length) {
554         recordLeakNonRefCountingOperation(leak);
555         return super.writeBytes(src, length);
556     }
557 
558     @Override
559     public ByteBuf writeBytes(ByteBuf src, int srcIndex, int length) {
560         recordLeakNonRefCountingOperation(leak);
561         return super.writeBytes(src, srcIndex, length);
562     }
563 
564     @Override
565     public ByteBuf writeBytes(byte[] src) {
566         recordLeakNonRefCountingOperation(leak);
567         return super.writeBytes(src);
568     }
569 
570     @Override
571     public ByteBuf writeBytes(byte[] src, int srcIndex, int length) {
572         recordLeakNonRefCountingOperation(leak);
573         return super.writeBytes(src, srcIndex, length);
574     }
575 
576     @Override
577     public ByteBuf writeBytes(ByteBuffer src) {
578         recordLeakNonRefCountingOperation(leak);
579         return super.writeBytes(src);
580     }
581 
582     @Override
583     public int writeBytes(InputStream in, int length) throws IOException {
584         recordLeakNonRefCountingOperation(leak);
585         return super.writeBytes(in, length);
586     }
587 
588     @Override
589     public int writeBytes(ScatteringByteChannel in, int length) throws IOException {
590         recordLeakNonRefCountingOperation(leak);
591         return super.writeBytes(in, length);
592     }
593 
594     @Override
595     public ByteBuf writeZero(int length) {
596         recordLeakNonRefCountingOperation(leak);
597         return super.writeZero(length);
598     }
599 
600     @Override
601     public int indexOf(int fromIndex, int toIndex, byte value) {
602         recordLeakNonRefCountingOperation(leak);
603         return super.indexOf(fromIndex, toIndex, value);
604     }
605 
606     @Override
607     public int bytesBefore(byte value) {
608         recordLeakNonRefCountingOperation(leak);
609         return super.bytesBefore(value);
610     }
611 
612     @Override
613     public int bytesBefore(int length, byte value) {
614         recordLeakNonRefCountingOperation(leak);
615         return super.bytesBefore(length, value);
616     }
617 
618     @Override
619     public int bytesBefore(int index, int length, byte value) {
620         recordLeakNonRefCountingOperation(leak);
621         return super.bytesBefore(index, length, value);
622     }
623 
624     @Override
625     public int forEachByte(ByteBufProcessor processor) {
626         recordLeakNonRefCountingOperation(leak);
627         return super.forEachByte(processor);
628     }
629 
630     @Override
631     public int forEachByte(int index, int length, ByteBufProcessor processor) {
632         recordLeakNonRefCountingOperation(leak);
633         return super.forEachByte(index, length, processor);
634     }
635 
636     @Override
637     public int forEachByteDesc(ByteBufProcessor processor) {
638         recordLeakNonRefCountingOperation(leak);
639         return super.forEachByteDesc(processor);
640     }
641 
642     @Override
643     public int forEachByteDesc(int index, int length, ByteBufProcessor processor) {
644         recordLeakNonRefCountingOperation(leak);
645         return super.forEachByteDesc(index, length, processor);
646     }
647 
648     @Override
649     public ByteBuf copy() {
650         recordLeakNonRefCountingOperation(leak);
651         return super.copy();
652     }
653 
654     @Override
655     public ByteBuf copy(int index, int length) {
656         recordLeakNonRefCountingOperation(leak);
657         return super.copy(index, length);
658     }
659 
660     @Override
661     public int nioBufferCount() {
662         recordLeakNonRefCountingOperation(leak);
663         return super.nioBufferCount();
664     }
665 
666     @Override
667     public ByteBuffer nioBuffer() {
668         recordLeakNonRefCountingOperation(leak);
669         return super.nioBuffer();
670     }
671 
672     @Override
673     public ByteBuffer nioBuffer(int index, int length) {
674         recordLeakNonRefCountingOperation(leak);
675         return super.nioBuffer(index, length);
676     }
677 
678     @Override
679     public ByteBuffer[] nioBuffers() {
680         recordLeakNonRefCountingOperation(leak);
681         return super.nioBuffers();
682     }
683 
684     @Override
685     public ByteBuffer[] nioBuffers(int index, int length) {
686         recordLeakNonRefCountingOperation(leak);
687         return super.nioBuffers(index, length);
688     }
689 
690     @Override
691     public ByteBuffer internalNioBuffer(int index, int length) {
692         recordLeakNonRefCountingOperation(leak);
693         return super.internalNioBuffer(index, length);
694     }
695 
696     @Override
697     public String toString(Charset charset) {
698         recordLeakNonRefCountingOperation(leak);
699         return super.toString(charset);
700     }
701 
702     @Override
703     public String toString(int index, int length, Charset charset) {
704         recordLeakNonRefCountingOperation(leak);
705         return super.toString(index, length, charset);
706     }
707 
708     @Override
709     public ByteBuf capacity(int newCapacity) {
710         recordLeakNonRefCountingOperation(leak);
711         return super.capacity(newCapacity);
712     }
713 
714     @Override
715     public ByteBuf retain() {
716         leak.record();
717         return super.retain();
718     }
719 
720     @Override
721     public ByteBuf retain(int increment) {
722         leak.record();
723         return super.retain(increment);
724     }
725 
726     @Override
727     public boolean release() {
728         leak.record();
729         return super.release();
730     }
731 
732     @Override
733     public boolean release(int decrement) {
734         leak.record();
735         return super.release(decrement);
736     }
737 
738     @Override
739     protected AdvancedLeakAwareByteBuf newLeakAwareByteBuf(
740             ByteBuf buf, ByteBuf trackedByteBuf, ResourceLeakTracker<ByteBuf> leakTracker) {
741         return new AdvancedLeakAwareByteBuf(buf, trackedByteBuf, leakTracker);
742     }
743 }