StreamUtil.java revision e6bf3e8dfa2804891a82075cb469b736321b4827
1package org.bouncycastle.asn1;
2
3import java.io.ByteArrayInputStream;
4import java.io.FileInputStream;
5import java.io.IOException;
6import java.io.InputStream;
7
8class StreamUtil
9{
10    private static final long  MAX_MEMORY = Runtime.getRuntime().maxMemory();
11
12    /**
13     * Find out possible longest length...
14     *
15     * @param in input stream of interest
16     * @return length calculation or MAX_VALUE.
17     */
18    static int findLimit(InputStream in)
19    {
20        if (in instanceof LimitedInputStream)
21        {
22            return ((LimitedInputStream)in).getRemaining();
23        }
24        else if (in instanceof ASN1InputStream)
25        {
26            return ((ASN1InputStream)in).getLimit();
27        }
28        else if (in instanceof ByteArrayInputStream)
29        {
30            return ((ByteArrayInputStream)in).available();
31        }
32        else if (in instanceof FileInputStream)
33        {
34            try
35            {
36                long  size = ((FileInputStream)in).getChannel().size();
37
38                if (size < Integer.MAX_VALUE)
39                {
40                    return (int)size;
41                }
42            }
43            catch (IOException e)
44            {
45                // ignore - they'll find out soon enough!
46            }
47        }
48
49        if (MAX_MEMORY > Integer.MAX_VALUE)
50        {
51            return Integer.MAX_VALUE;
52        }
53
54        return (int)MAX_MEMORY;
55    }
56
57    static int calculateBodyLength(
58        int length)
59    {
60        int count = 1;
61
62        if (length > 127)
63        {
64            int size = 1;
65            int val = length;
66
67            while ((val >>>= 8) != 0)
68            {
69                size++;
70            }
71
72            for (int i = (size - 1) * 8; i >= 0; i -= 8)
73            {
74                count++;
75            }
76        }
77
78        return count;
79    }
80
81    static int calculateTagLength(int tagNo)
82        throws IOException
83    {
84        int length = 1;
85
86        if (tagNo >= 31)
87        {
88            if (tagNo < 128)
89            {
90                length++;
91            }
92            else
93            {
94                byte[] stack = new byte[5];
95                int pos = stack.length;
96
97                stack[--pos] = (byte)(tagNo & 0x7F);
98
99                do
100                {
101                    tagNo >>= 7;
102                    stack[--pos] = (byte)(tagNo & 0x7F | 0x80);
103                }
104                while (tagNo > 127);
105
106                length += stack.length - pos;
107            }
108        }
109
110        return length;
111    }
112}
113