Memory.java revision 8fbc397fc09158bee0bc0cb231c609c4c6e9fc15
1adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project/*
2adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project *  Licensed to the Apache Software Foundation (ASF) under one or more
3adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project *  contributor license agreements.  See the NOTICE file distributed with
4adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project *  this work for additional information regarding copyright ownership.
5adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project *  The ASF licenses this file to You under the Apache License, Version 2.0
6adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project *  (the "License"); you may not use this file except in compliance with
7adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project *  the License.  You may obtain a copy of the License at
8adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project *
9adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project *     http://www.apache.org/licenses/LICENSE-2.0
10adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project *
11adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project *  Unless required by applicable law or agreed to in writing, software
12adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project *  distributed under the License is distributed on an "AS IS" BASIS,
13adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project *  See the License for the specific language governing permissions and
15adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project *  limitations under the License.
16adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project */
17adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project
18adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Projectpackage org.apache.harmony.luni.platform;
19adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project
20adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Projectimport java.io.IOException;
218510524dab13e0acc1babf22cbc55002fb122777Elliott Hughesimport java.nio.ByteOrder;
228510524dab13e0acc1babf22cbc55002fb122777Elliott Hughesimport java.nio.channels.FileChannel.MapMode;
23adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project
24adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project/**
2571961a4957d24f62f7adc5f0549e236018589631Elliott Hughes * This class enables direct access to memory.
26f46d2ce4d4c92d16e2574f57f70fc5477dc12697Elliott Hughes *
27f46d2ce4d4c92d16e2574f57f70fc5477dc12697Elliott Hughes * @hide - we should move this in with the NIO stuff it supports, and make it package-private again
28adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project */
29f46d2ce4d4c92d16e2574f57f70fc5477dc12697Elliott Hughespublic final class OSMemory {
3071961a4957d24f62f7adc5f0549e236018589631Elliott Hughes    private OSMemory() { }
31adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project
32adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project    /**
338fbc397fc09158bee0bc0cb231c609c4c6e9fc15Elliott Hughes     * Used to optimize nio heap buffer bulk get operations. 'dst' must be a primitive array.
346944bea4a129dc2d4be687c72f2a9f228ec532bcElliott Hughes     * 'dstOffset' is measured in units of 'sizeofElements' bytes.
356944bea4a129dc2d4be687c72f2a9f228ec532bcElliott Hughes     */
368fbc397fc09158bee0bc0cb231c609c4c6e9fc15Elliott Hughes    public static native void unsafeBulkGet(Object dst, int dstOffset, int byteCount,
376944bea4a129dc2d4be687c72f2a9f228ec532bcElliott Hughes            byte[] src, int srcOffset, int sizeofElements, boolean swap);
386944bea4a129dc2d4be687c72f2a9f228ec532bcElliott Hughes
396944bea4a129dc2d4be687c72f2a9f228ec532bcElliott Hughes    /**
408fbc397fc09158bee0bc0cb231c609c4c6e9fc15Elliott Hughes     * Used to optimize nio heap buffer bulk put operations. 'src' must be a primitive array.
418fbc397fc09158bee0bc0cb231c609c4c6e9fc15Elliott Hughes     * 'srcOffset' is measured in units of 'sizeofElements' bytes.
428fbc397fc09158bee0bc0cb231c609c4c6e9fc15Elliott Hughes     */
438fbc397fc09158bee0bc0cb231c609c4c6e9fc15Elliott Hughes    public static native void unsafeBulkPut(byte[] dst, int dstOffset, int byteCount,
448fbc397fc09158bee0bc0cb231c609c4c6e9fc15Elliott Hughes            Object src, int srcOffset, int sizeofElements, boolean swap);
458fbc397fc09158bee0bc0cb231c609c4c6e9fc15Elliott Hughes
468fbc397fc09158bee0bc0cb231c609c4c6e9fc15Elliott Hughes    /**
474d68282a79fb0417f43efdef41b9a920385bddedElliott Hughes     * Returns the address of byteCount bytes of memory. Unlike the corresponding C library
484d68282a79fb0417f43efdef41b9a920385bddedElliott Hughes     * function, the memory returned has been zero-initialized.
498510524dab13e0acc1babf22cbc55002fb122777Elliott Hughes     */
504d68282a79fb0417f43efdef41b9a920385bddedElliott Hughes    public static native int malloc(int byteCount) throws OutOfMemoryError;
51adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project
52adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project    /**
53adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project     * Deallocates space for a memory block that was previously allocated by a
54adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project     * call to {@link #malloc(int) malloc(int)}. The number of bytes freed is
55adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project     * identical to the number of bytes acquired when the memory block was
568510524dab13e0acc1babf22cbc55002fb122777Elliott Hughes     * allocated. If <code>address</code> is zero the method does nothing.
578510524dab13e0acc1babf22cbc55002fb122777Elliott Hughes     * <p>
58adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project     * Freeing a pointer to a memory block that was not allocated by
598510524dab13e0acc1babf22cbc55002fb122777Elliott Hughes     * <code>malloc()</code> has unspecified effect.
608510524dab13e0acc1babf22cbc55002fb122777Elliott Hughes     * </p>
61f5597e626ecf7949d249dea08c1a2964d890ec11Jesse Wilson     *
628510524dab13e0acc1babf22cbc55002fb122777Elliott Hughes     * @param address
638510524dab13e0acc1babf22cbc55002fb122777Elliott Hughes     *            the address of the memory block to deallocate.
64adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project     */
658510524dab13e0acc1babf22cbc55002fb122777Elliott Hughes    public static native void free(int address);
66adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project
67adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project    /**
68adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project     * Copies <code>length</code> bytes from <code>srcAddress</code> to
698510524dab13e0acc1babf22cbc55002fb122777Elliott Hughes     * <code>destAddress</code>. Where any part of the source memory block
708510524dab13e0acc1babf22cbc55002fb122777Elliott Hughes     * and the destination memory block overlap <code>memmove()</code> ensures
718510524dab13e0acc1babf22cbc55002fb122777Elliott Hughes     * that the original source bytes in the overlapping region are copied
728510524dab13e0acc1babf22cbc55002fb122777Elliott Hughes     * before being overwritten.
738510524dab13e0acc1babf22cbc55002fb122777Elliott Hughes     * <p>
748510524dab13e0acc1babf22cbc55002fb122777Elliott Hughes     * The behavior is unspecified if
758510524dab13e0acc1babf22cbc55002fb122777Elliott Hughes     * <code>(srcAddress ... srcAddress + length)</code> and
768510524dab13e0acc1babf22cbc55002fb122777Elliott Hughes     * <code>(destAddress ... destAddress + length)</code> are not both wholly
778510524dab13e0acc1babf22cbc55002fb122777Elliott Hughes     * within the range that was previously allocated using
788510524dab13e0acc1babf22cbc55002fb122777Elliott Hughes     * <code>malloc()</code>.
798510524dab13e0acc1babf22cbc55002fb122777Elliott Hughes     * </p>
80f5597e626ecf7949d249dea08c1a2964d890ec11Jesse Wilson     *
818510524dab13e0acc1babf22cbc55002fb122777Elliott Hughes     * @param destAddress
828510524dab13e0acc1babf22cbc55002fb122777Elliott Hughes     *            the address of the destination memory block.
838510524dab13e0acc1babf22cbc55002fb122777Elliott Hughes     * @param srcAddress
848510524dab13e0acc1babf22cbc55002fb122777Elliott Hughes     *            the address of the source memory block.
858510524dab13e0acc1babf22cbc55002fb122777Elliott Hughes     * @param length
868510524dab13e0acc1babf22cbc55002fb122777Elliott Hughes     *            the number of bytes to move.
87adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project     */
888510524dab13e0acc1babf22cbc55002fb122777Elliott Hughes    public static native void memmove(int destAddress, int srcAddress, long length);
89adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project
901b9018762e87e3dda69020248817011efd5a40dcElliott Hughes    public static native byte peekByte(int address);
911b9018762e87e3dda69020248817011efd5a40dcElliott Hughes    public static native int peekInt(int address, boolean swap);
921b9018762e87e3dda69020248817011efd5a40dcElliott Hughes    public static native long peekLong(int address, boolean swap);
931b9018762e87e3dda69020248817011efd5a40dcElliott Hughes    public static native short peekShort(int address, boolean swap);
94adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project
95692222b08ff88eb92b523bf4780d7ea17a23aa80Elliott Hughes    public static native void peekByteArray(int address, byte[] dst, int dstOffset, int byteCount);
96961da1e7487bdb8ad8ac226d4f2789d003aa87b9Elliott Hughes    public static native void peekCharArray(int address, char[] dst, int dstOffset, int charCount, boolean swap);
97961da1e7487bdb8ad8ac226d4f2789d003aa87b9Elliott Hughes    public static native void peekDoubleArray(int address, double[] dst, int dstOffset, int doubleCount, boolean swap);
98961da1e7487bdb8ad8ac226d4f2789d003aa87b9Elliott Hughes    public static native void peekFloatArray(int address, float[] dst, int dstOffset, int floatCount, boolean swap);
99692222b08ff88eb92b523bf4780d7ea17a23aa80Elliott Hughes    public static native void peekIntArray(int address, int[] dst, int dstOffset, int intCount, boolean swap);
100961da1e7487bdb8ad8ac226d4f2789d003aa87b9Elliott Hughes    public static native void peekLongArray(int address, long[] dst, int dstOffset, int longCount, boolean swap);
101961da1e7487bdb8ad8ac226d4f2789d003aa87b9Elliott Hughes    public static native void peekShortArray(int address, short[] dst, int dstOffset, int shortCount, boolean swap);
102adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project
1031b9018762e87e3dda69020248817011efd5a40dcElliott Hughes    public static native void pokeByte(int address, byte value);
1041b9018762e87e3dda69020248817011efd5a40dcElliott Hughes    public static native void pokeInt(int address, int value, boolean swap);
1051b9018762e87e3dda69020248817011efd5a40dcElliott Hughes    public static native void pokeLong(int address, long value, boolean swap);
1061b9018762e87e3dda69020248817011efd5a40dcElliott Hughes    public static native void pokeShort(int address, short value, boolean swap);
107adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project
108692222b08ff88eb92b523bf4780d7ea17a23aa80Elliott Hughes    public static native void pokeByteArray(int address, byte[] src, int offset, int count);
109692222b08ff88eb92b523bf4780d7ea17a23aa80Elliott Hughes    public static native void pokeCharArray(int address, char[] src, int offset, int count, boolean swap);
110692222b08ff88eb92b523bf4780d7ea17a23aa80Elliott Hughes    public static native void pokeDoubleArray(int address, double[] src, int offset, int count, boolean swap);
111692222b08ff88eb92b523bf4780d7ea17a23aa80Elliott Hughes    public static native void pokeFloatArray(int address, float[] src, int offset, int count, boolean swap);
112692222b08ff88eb92b523bf4780d7ea17a23aa80Elliott Hughes    public static native void pokeIntArray(int address, int[] src, int offset, int count, boolean swap);
113692222b08ff88eb92b523bf4780d7ea17a23aa80Elliott Hughes    public static native void pokeLongArray(int address, long[] src, int offset, int count, boolean swap);
114692222b08ff88eb92b523bf4780d7ea17a23aa80Elliott Hughes    public static native void pokeShortArray(int address, short[] src, int offset, int count, boolean swap);
11571961a4957d24f62f7adc5f0549e236018589631Elliott Hughes
1168510524dab13e0acc1babf22cbc55002fb122777Elliott Hughes    private static native int mmapImpl(int fd, long offset, long size, int mapMode);
1173c6ff817ba94b64cf24014acff7201859410fb13Elliott Hughes
1188510524dab13e0acc1babf22cbc55002fb122777Elliott Hughes    public static int mmap(int fd, long offset, long size, MapMode mapMode) throws IOException {
1193c6ff817ba94b64cf24014acff7201859410fb13Elliott Hughes        // Check just those errors mmap(2) won't detect.
1203c6ff817ba94b64cf24014acff7201859410fb13Elliott Hughes        if (offset < 0 || size < 0 || offset > Integer.MAX_VALUE || size > Integer.MAX_VALUE) {
1213c6ff817ba94b64cf24014acff7201859410fb13Elliott Hughes            throw new IllegalArgumentException("offset=" + offset + " size=" + size);
1223c6ff817ba94b64cf24014acff7201859410fb13Elliott Hughes        }
1238510524dab13e0acc1babf22cbc55002fb122777Elliott Hughes        int intMode = 0; // MapMode.PRIVATE
1248510524dab13e0acc1babf22cbc55002fb122777Elliott Hughes        if (mapMode == MapMode.READ_ONLY) {
1258510524dab13e0acc1babf22cbc55002fb122777Elliott Hughes            intMode = 1;
1268510524dab13e0acc1babf22cbc55002fb122777Elliott Hughes        } else if (mapMode == MapMode.READ_WRITE) {
1278510524dab13e0acc1babf22cbc55002fb122777Elliott Hughes            intMode = 2;
1288510524dab13e0acc1babf22cbc55002fb122777Elliott Hughes        }
1298510524dab13e0acc1babf22cbc55002fb122777Elliott Hughes        return mmapImpl(fd, offset, size, intMode);
130adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project    }
131adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project
1321b9018762e87e3dda69020248817011efd5a40dcElliott Hughes    public static native void munmap(int addr, long size);
133adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project
1348510524dab13e0acc1babf22cbc55002fb122777Elliott Hughes    public static native void load(int addr, long size);
135adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project
1368510524dab13e0acc1babf22cbc55002fb122777Elliott Hughes    public static native boolean isLoaded(int addr, long size);
137adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project
1381b9018762e87e3dda69020248817011efd5a40dcElliott Hughes    public static native void msync(int addr, long size);
139adc854b798c1cfe3bfd4c27d68d5cee38ca617daThe Android Open Source Project}
140