001/* 002 * Copyright 2013 Alex Kasko (alexkasko.com) 003 * 004 * Licensed under the Apache License, Version 2.0 (the "License"); 005 * you may not use this file except in compliance with the License. 006 * You may obtain a copy of the License at 007 * 008 * http://www.apache.org/licenses/LICENSE-2.0 009 * 010 * Unless required by applicable law or agreed to in writing, software 011 * distributed under the License is distributed on an "AS IS" BASIS, 012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 013 * See the License for the specific language governing permissions and 014 * limitations under the License. 015 */ 016 017package com.alexkasko.unsafe.offheap; 018 019import com.alexkasko.unsafe.bytearray.ByteArrayTool; 020 021import java.util.concurrent.atomic.AtomicBoolean; 022 023/** 024 * Implementation of {@link com.alexkasko.unsafe.offheap.OffHeapMemory} 025 * using byte array effectively making it <b>OnHeap</b> memory 026 * 027 * @author alexkasko 028 * Date: 1/14/13 029*/ 030class OnHeapMemory extends OffHeapMemory { 031 032 private final ByteArrayTool bt; 033 private byte[] mem; 034 private final AtomicBoolean disposed = new AtomicBoolean(false); 035 036 OnHeapMemory(ByteArrayTool bt, long bytes) { 037 if(bytes > Integer.MAX_VALUE) throw new IllegalArgumentException( 038 "Long-sized allocations are not supported by [" + getClass().getName() + "]"); 039 this.bt = bt; 040 this.mem = new byte[(int) bytes]; 041 } 042 043 /** 044 * {@inheritDoc} 045 */ 046 @Override 047 public boolean isUnsafe() { 048 return false; 049 } 050 051 /** 052 * {@inheritDoc} 053 */ 054 @Override 055 public long length() { 056 return mem.length; 057 } 058 059 /** 060 * {@inheritDoc} 061 */ 062 @Override 063 public void free() { 064 if(!disposed.compareAndSet(false, true)) return; 065 this.mem = null; 066 } 067 068 /** 069 * {@inheritDoc} 070 */ 071 @Override 072 public void put(long offset, byte[] buffer, int bufferOffset, int bytes) { 073 bt.copy(buffer, bufferOffset, mem, (int) offset, bytes); 074 } 075 076 /** 077 * {@inheritDoc} 078 */ 079 @Override 080 public void put(long offset, byte[] buffer) { 081 bt.copy(buffer, 0, mem, (int) offset, buffer.length); 082 } 083 084 /** 085 * {@inheritDoc} 086 */ 087 @Override 088 public void get(long offset, byte[] buffer, int bufferOffset, int bytes) { 089 bt.copy(mem, (int) offset, buffer, bufferOffset, bytes); 090 } 091 092 /** 093 * {@inheritDoc} 094 */ 095 @Override 096 public void get(long offset, byte[] buffer) { 097 bt.copy(mem, (int) offset, buffer, 0, buffer.length); 098 } 099 100 /** 101 * {@inheritDoc} 102 */ 103 @Override 104 public byte getByte(long offset) { 105 return bt.getByte(mem, (int) offset); 106 } 107 108 /** 109 * {@inheritDoc} 110 */ 111 @Override 112 public void putByte(long offset, byte value) { 113 bt.putByte(mem, (int) offset, value); 114 } 115 116 /** 117 * {@inheritDoc} 118 */ 119 @Override 120 public short getUnsignedByte(long offset) { 121 return bt.getUnsignedByte(mem, (int) offset); 122 } 123 124 /** 125 * {@inheritDoc} 126 */ 127 @Override 128 public void putUnsignedByte(long offset, short value) { 129 bt.putUnsignedByte(mem, (int) offset, value); 130 } 131 132 /** 133 * {@inheritDoc} 134 */ 135 @Override 136 public short getShort(long offset) { 137 return bt.getShort(mem, (int) offset); 138 } 139 140 /** 141 * {@inheritDoc} 142 */ 143 @Override 144 public void putShort(long offset, short value) { 145 bt.putShort(mem, (int) offset, value); 146 } 147 148 /** 149 * {@inheritDoc} 150 */ 151 @Override 152 public int getUnsignedShort(long offset) { 153 return bt.getUnsignedShort(mem, (int) offset); 154 } 155 156 /** 157 * {@inheritDoc} 158 */ 159 @Override 160 public void putUnsignedShort(long offset, int value) { 161 bt.putUnsignedShort(mem, (int) offset, value); 162 } 163 164 /** 165 * {@inheritDoc} 166 */ 167 @Override 168 public int getInt(long offset) { 169 return bt.getInt(mem, (int) offset); 170 } 171 172 /** 173 * {@inheritDoc} 174 */ 175 @Override 176 public void putInt(long offset, int value) { 177 bt.putInt(mem, (int) offset, value); 178 } 179 180 /** 181 * {@inheritDoc} 182 */ 183 @Override 184 public long getUnsignedInt(long offset) { 185 return bt.getUnsignedInt(mem, (int) offset); 186 } 187 188 /** 189 * {@inheritDoc} 190 */ 191 @Override 192 public void putUnsignedInt(long offset, long value) { 193 bt.putUnsignedInt(mem, (int) offset, value); 194 } 195 196 /** 197 * {@inheritDoc} 198 */ 199 @Override 200 public long getLong(long offset) { 201 return bt.getLong(mem, (int) offset); 202 } 203 204 /** 205 * {@inheritDoc} 206 */ 207 @Override 208 public void putLong(long offset, long value) { 209 bt.putLong(mem, (int) offset, value); 210 } 211 212 /** 213 * {@inheritDoc} 214 */ 215 @Override 216 public void copy(long offset, OffHeapMemory destination, long destOffset, long bytes) { 217 OnHeapMemory dest = (OnHeapMemory) destination; 218 bt.copy(mem, (int) offset, dest.mem, (int) destOffset, (int) bytes); 219 } 220 221 /** 222 * {@inheritDoc} 223 */ 224 @Override 225 public OffHeapMemory clone() { 226 OnHeapMemory res = new OnHeapMemory(bt, mem.length); 227 this.copy(0, res, 0, mem.length); 228 return res; 229 } 230 231 /** 232 * {@inheritDoc} 233 */ 234 @Override 235 public String toString() { 236 final StringBuilder sb = new StringBuilder(); 237 sb.append("OnHeapMemory"); 238 sb.append("{bt=").append(bt); 239 sb.append(", length=").append(!disposed.get() ? mem.length : -1); 240 sb.append(", disposed=").append(disposed); 241 sb.append('}'); 242 return sb.toString(); 243 } 244}