Main.java Source code

Java tutorial

Introduction

Here is the source code for Main.java

Source

//package com.java2s;
/*
 * Copyright (C) 2014 The Android Open Source Project
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

import java.util.Arrays;

public class Main {
    private static final Object scratchEscapePositionsLock = new Object();
    /**
     * Temporary store for positions of escape codes in {@link #unescapeStream(byte[], int)}. Guarded
     * by {@link #scratchEscapePositionsLock}.
     */
    private static int[] scratchEscapePositions = new int[10];

    /**
     * Unescapes {@code data} up to the specified limit, replacing occurrences of [0, 0, 3] with
     * [0, 0]. The unescaped data is returned in-place, with the return value indicating its length.
     * <p>
     * Executions of this method are mutually exclusive, so it should not be called with very large
     * buffers.
     *
     * @param data The data to unescape.
     * @param limit The limit (exclusive) of the data to unescape.
     * @return The length of the unescaped data.
     */
    public static int unescapeStream(byte[] data, int limit) {
        synchronized (scratchEscapePositionsLock) {
            int position = 0;
            int scratchEscapeCount = 0;
            while (position < limit) {
                position = findNextUnescapeIndex(data, position, limit);
                if (position < limit) {
                    if (scratchEscapePositions.length <= scratchEscapeCount) {
                        // Grow scratchEscapePositions to hold a larger number of positions.
                        scratchEscapePositions = Arrays.copyOf(scratchEscapePositions,
                                scratchEscapePositions.length * 2);
                    }
                    scratchEscapePositions[scratchEscapeCount++] = position;
                    position += 3;
                }
            }

            int unescapedLength = limit - scratchEscapeCount;
            int escapedPosition = 0; // The position being read from.
            int unescapedPosition = 0; // The position being written to.
            for (int i = 0; i < scratchEscapeCount; i++) {
                int nextEscapePosition = scratchEscapePositions[i];
                int copyLength = nextEscapePosition - escapedPosition;
                System.arraycopy(data, escapedPosition, data, unescapedPosition, copyLength);
                unescapedPosition += copyLength;
                data[unescapedPosition++] = 0;
                data[unescapedPosition++] = 0;
                escapedPosition += copyLength + 3;
            }

            int remainingLength = unescapedLength - unescapedPosition;
            System.arraycopy(data, escapedPosition, data, unescapedPosition, remainingLength);
            return unescapedLength;
        }
    }

    private static int findNextUnescapeIndex(byte[] bytes, int offset, int limit) {
        for (int i = offset; i < limit - 2; i++) {
            if (bytes[i] == 0x00 && bytes[i + 1] == 0x00 && bytes[i + 2] == 0x03) {
                return i;
            }
        }
        return limit;
    }
}