Force memory allocation in Java - java

I am aware that memory allocation is not explicitly required in Java, as the JVM handles allocation behind the scenes. Even though I am not required to allocate memory, for the sake of testing a memory greedy application, how would I be able to hold objects of certain numbers of bytes?
The current solution is to instantiate arrays of the primitive 'byte'. If I want to hold 5 MB worth of objects, I create an array of bytes.
byte[] b = new byte[5000000];
Is there a better way to explicitly allocate memory in a Java JVM, if only for the sake creating / releasing objects of known size for some unit tests?

There isn't really a better way of doing it. 'new' is the only way to explicitly occupy memory (except allocating stack by calling a method, for example).
byte b = new byte[MEM_SIZE];
is the most controllable way of doing it. It won't allocate exactly 5000000 bytes, thanks to object overhead, but it's pretty close.

Related

how much memory is a stack object allocated upon creation?

I was wondering- when defining a new stack through the stack class
Stack stack=new Stack();
How much memory is allocated to it? It cannot depend on the amount of N objects (like arrays and lists, for example) because it is initialized without any data regarding the amount of objects that would be placed in.
However, it also doesn't make a lot of sense that it'd have a fixed amount of memory like an intor double for example, because you constantly place objects in it.
Does push command increases the memory allocation of the stack?
I assume it is placed in the 'heap' memory?
Thanks!
I'm speaking from C#, so bear with me; Whenever you allocate memory for a local variable, it gets allocated on the stack, heap is for things like objects, which allocates a reference to the object and then the actual object, then the object reference gets used by the garbage collector to go through and figure out what objects need to be cleaned up and which ones don't.
In this case, I believe you are allocating the object on the heap, because all a "stack" object is, is a filo data structure.
Stacks in Java only store primitives that exist within a local scope, ergo the stack size in Java is usually pretty small, the size however depends on several factors and is variable at runtime, the initial size for example is typically calculated based on how much memory the compiler thinks it will need to run, then as it grows it will increase in size (I think Windows for example increases the stack by pages, which is 256 bytes of memory, but don't hold me to that.)
In your case, since you are asking about the initial size of an uninitialized stack object, the size is the size of the stack object, and it changes as you add elements to it.
Hope that helps.
Stack extends Vector, and Stack() calls Vector() implicitly, which uses a default initial capacity of 10.
Stack inherits from Vector. The default constructor of Vector initializes an array with size 10.

Java Object[] and cache strading

As we know when memory is moved to L caches on cpu it is moved with cachelines, thus the whole cache strading performance optimization...
Well in java when we define an array jmm guarantees that memory for each element will be allocated sequentially. However if we have array of references, those references can point randomly to different places in the memory.
My question is does java allocate actual objects memory sequentially? What optimizations do we have under the hood for this?
For example if we declare int[] we are confident those are all actually sequential in memory, but if we define a NewType (like struct) that has two int fields in it, and declare NewType[] will java figure out and keep actual memory sequentially or not?
My question is does java allocate actual objects memory sequentially?
This is not guaranteed, but most of the time the OpenJDK/Oracle JVM does. Some of the times it doesn't are;
when you allocate a large object in tenured space,
your TLAB is full and you need to get another one.
However, within the TLAB, it just allocates sequentially in memory.
declare NewType[] will java figure out and keep actual memory sequentially or not?
Java doesn't figure out anything, nor does it go out of it's way to allocate objects randomly in memory. In general, each new object will be immediately after the last one.
but if we define a NewType (like struct) that has two int fields in it, and declare NewType[] will java figure out and keep actual memory sequentially or not?
In this scenario java is not very cache-friendly because apart from primitive types java arrays are not packed data structures, they are arrays of references pointing to objects allocated elsewhere in memory.
I.e. there will be at least one level of indirection from the array to the object itself. This problem is often referred to as "pointer chasing".
I.e. usually the memory layout will look like this:
HlRRRRRRRRRRRRRRRRRRRRRRRRR0HR0iii0HR0iii0HR0iii0HR0iii0HR0iii0HR0iii0HR0iii0
Array | Obj | Obj | Obj | Obj | Obj | Obj | Obj |
H = object header
l = array length
R = reference
i = int
0 = various types of padding
You can use jol to inspect the memory layout of objects.
The JDK devs are working on Value types as part of project valhalla that will eventually allow packed arrays to exist, which may be needed as part of project panama, but this still is far off into the future.
In the meantime there are 3rd-party projects aim to provide similar features:
https://github.com/ObjectLayout/ObjectLayout
https://github.com/RichardWarburton/packed-objects-experiments
Other projects either use off-heap storage (e.g. via sun.misc.Unsafe) or views on ByteBuffer / byte[] arrays to create packed, cache-friendly data structures at the expense of more complicated APIs.

Is array in java virtually sequential memory data structure? or physically sequential?

I try to find what is difference between primitive java 'array' and 'List' data structure (like ArrayList), and find articles or Q&A like this (Difference between List and Array). Many articles including that link point that java primitive 'array' is 'sequential memory'. In this point, what is sequential exactly? is this really sequential in physical memory? or sequential in virtual memory? My guess is sequential in virtual memory, because OS assigns physical memory in general and application(JVM) doesn't care about specific memory allocation. But I do not know exact answer.
A Java array is sequential in virtual memory not necessarily in physical memory.
A user-space application (such as a JVM) has no say over whether the physical pages that make up its virtual address space are contiguous in memory. And in fact, it has no way of even knowing this in typical modern operating systems. This is all hidden from a user-space application by the machine's virtual memory hardware and (user-space) instruction set architecture.
Looking at the JVM spec is not going to be instructive on the physical memory issue. It is simply not relevant / out of scope.
The JVM spec doesn't mandate that arrays are contiguous in virtual memory. However, (hypothetical) array implementations that involved non-contiguous virtual memory would lead to expensive array operations, so you are unlikely to find a mainstream JVM that does this.
References:
JVM Spec 2.7 says:
"The Java Virtual Machine does not mandate any particular internal structure for objects."
Other parts of the spec imply that "objects" refers here to BOTH instances of classes AND arrays.
JVM Spec 2.4 talks about arrays, but it doesn't mention how they are represented in memory.
The difference between arrays and ArrayLists are at a higher level. Arrays have a fixed size. ArrayLists have a variable size. But under the hood, an ArrayList is implemented using a (single) array ... which can be reallocated (i.e. replaced) if the list grows too big.
You would have to look at the JVM specs to see whether any such requirement is made (whether arrays need to be sequential memory or not), but for efficiency purposes it makes sense that an array would be allocated in a malloc type way.
As for virtual vs. physical, everything (above the OS) works with virtual memory. The JVM isn't low level enough to have access to something the kernel does at Ring-0.
And lastly, why are you interested, are you writing your own JVM?
JVM gets virtual sequential memory from OS. Only at OS level it is possible to assign physical memory sequentially.
Also it's important to not confuse between sequential memory allocation and sequential access - sequential access means that a group of elements is accessed in a predetermined, ordered sequence. A data structure is said to have sequential access if one can only visit the values it contains in one particular order. The canonical example is the linked list.
Whereas sequential memory meaning assigning of sequential memory (not necessarily physically sequential, but virtually sequential).
Besides the link you posted some major differences between Array and ArrayList are:
Array is fixed in size, ArrayList is dynamic in size
Array can store primitives, ArrayList can only store Objects (Wrapper
types for primitives)
You can use generics with ArrayList
You can use add() method to insert element into ArrayList and you can
simply use assignment operator to store element into Array
References: Java67 article, Wikipedia
this might be an interesting article explaining your question.
Arrays are also objects in Java, so how an object looks like in memory applies to an array.
To summarise:
class A {
int x;
int y;
}
public void m1() {
int i = 0;
m2();
}
public void m2() {
A a = new A();
}
When m1 is invoked, a new frame (Frame-1) is pushed into the stack, and local variable i is also created in Frame-1.
Then m2 is invoked inside of m1, another new frame (Frame-2) is pushed into the stack. In m2, an object of class A is created in the heap and reference variable is put in Frame-2.
Physical memory locations are out of your hands and will be assigned by the OS
http://www.programcreek.com/2013/04/what-does-a-java-array-look-like-in-memory/

Explain the difference between contiguous allocation (memory held in a heap in the stack) vs. memory in a heap [closed]

Closed. This question needs details or clarity. It is not currently accepting answers.
Want to improve this question? Add details and clarify the problem by editing this post.
Closed 8 years ago.
Improve this question
Explain the difference between contiguous allocation (memory held in a heap in the stack) vs. memory in a heap.
I'm new at this and not entirely sure.
The question isn't contiguous versus heap, but automatic versus heap.
Automatic storage is set up on entry to a block of code -- traditionally on entry to a function or method -- and discarded when that function returns, so its memory space on the stack can be reused by the next function call. That's how most local variables are handled. Obviously this isn't useful for anything which is intended to persist past the end of that function call.
In Java, objects are never allocated from automatic storage. Instead, they are allocated from the heap, on demands, when the new operation is performed. There are several reasons for this which, frankly, unless you're designing a programming language you don't really need to know about and it's too large a topic to cover here. The important thing is that since they were obtained from the heap, their lifetime is independent of the stack frame. Since Java is a garbage-collected language, their memory will be automatically recovered for reuse sometime after that last reference to them goes away -- again, the details are too large a topic to cover here, but basically you can trust that the GC comes through periodically to pick up the clothes we dropped on the floor and toss them into the laundry.
A stack frame only exists for the life of a method call, which means that memory is allocated to provide storage for all your local variables and method parameters that are used in some way that assist helping the method achieve its goals of whatever task it set out to achieve.
Examples of memory storage in a stack frame are temporary pointers that are used to keep track of an index position in an array which you are iterating through. Once the loop is finished, the stack frame would be popped off the stack, which means all the temporary memory allocated for the local variables and method parameters that existed are released back into the system.
The heap is different because it is where objects live, not "pointers" to objects.
When I was learning I found it hard to work out the difference between the two.
The key point that helped me was that, a pointer to an object is kept in a stack frame, it has a little bit of temporary memory allocated that exists for the life time of the method call. Thus, you can only access an object when the method is in "scope".
The pointer contains a memory address that leads to the location of the object stored on the heap. This allows you to reference the object to change the objects state at a later time.
public static void main(String[] args)
{
Person person = new Person("Steven", 30);
}
When you run this program:
new keyword means java will allocate memory on the heap for the space required to store the Person objects instance variables.
The important part to understand is, no memory is required to store an objects methods. When a method is called, a new stack frame is created which allocates temporary memory for the duration of the method call. Using the example above, a Person has 2 instance variables, a String name and int age. This means that the memory required for this Person object is the required memory to store a reference variable of type String (bit pattern of the memory address of a String object on the heap) and memory to hold the bit pattern of an int.
Lastly, the main method is a stack frame too, so when main finishes, you no longer have a reference to a Person object or access to any temporary variables that may have existed in main.
This is true for any method, if you have a method that creates an object but doesn't return the reference to that object, then you can never access the object and the java garbage collector comes along at a later time and cleans up all the objects on the heap that don't have references pointing to them.
If you are starting out, I highly recommend head first java. It is a great book IMO and covers these topics in easy to understand ways.
When we talk about memory or disc allocation, the word "contiguous" simply means "without any gaps".
A single stack or heap memory allocation is always contiguous ... in every programming language runtime I've ever encountered where it makes sense to talk about allocations at all.
A sequence of allocations is contiguous if there is no gap between the individual allocations.
This is orthogonal to stack versus heap. Both stack allocations and heap allocations can be contiguous ... or non-contiguous.
Well ... not quite orthogonal.
If you are talking about strictly contiguous memory addresses (physical or virtual), a typical heap node consists of the area of memory that the application can use, plus a small node header. So, if you look at the available memory for two consecutive heap nodes, there is a gap ... comprising the node header ... that prevents the two regions being used by the application as a single contiguous region. (And you'd better not try 'cos if you overwrite the node header, bad things could happen.)
However, when we are talking about Java this is not relevant. Java does not allow an application to join objects or arrays together. (That would be a fundamental violation of runtime type safety.) So the notional gap in the address ranges doesn't matter. In the Java context, we would say that two objects are contiguous, ignoring the heap node / object header.
Besides, in Java you can't explicitly allocate things on the heap either. In a classical JVM, only local variables comprising primitive types and references go on the stack. There is no way to say "allocate this array on the stack". (The JVM might do the latter under certain circumstances, but it is entirely transparent to the application, and certainly not something that you could make use of.)

Memory allocation : How much space does a reference occupy in Java?

In Java we have written a code:
A a1;
a1 = new A();
How many bytes of memory is reserved when compiler compiles the code:
A a1;
That's not specified by the Java standard and thus you should not worry about it.
Technically, references are usually as big as the machine's word size, i.e. 32 bit on a 32 bit machine and 64 bit on a 64 bit machine, though some 64 bit JVMs use special magic to allow 32 bit references.
One pointer's worth of memory is used on the stack. That should be 32 bits (4 bytes) unless your machine's in 64-bits mode.
edit:
I see that some people are confused and think that the A object itself is allocated on the stack. That is not the case in Java: all objects are allocated on the heap (modulo JIT optimizations of course). The line A a1; simply allocates pointer a1, initially set to NULL. The pointer itself is in the stack, though of course what it points to will be on the heap. The later call to new A() will allocate an A object on the heap, and the size of that allocation does depend on what's in A.
That depends on the platform and the implementation. For a 32-bit platform, a 4 byte pointer is used behind the scenes on object instances, regardless of the size of class A.
Edit:
The Java compiler does not reserve any memory for this, that's the runtime's (to be exact, the JIT's) responsibility.
A variable reference is a handle to an object on the heap, so it will take up a fixed amount (depending on the JVM implementation). However, just for that line, the compiler may not take up anything, since the variable has not been initialized yet. This is statically checked by the compiler, so it will know when it needs to allocate the variable and may in fact allocate it only when it is first assigned.
If you had a method:
public static void method() {
A a1;
}
I would expect the compiler to optimize it out completely, as it can't do anything with it.
All that being said, in Java programming, you just don't worry about these things, they are determined by the JVM implementation and Java is not suitable for byte-level memory concerns. If you are counting bytes like that, you should be using C or some similarly close-to-the-metal language.
Was your question: How much space does a reference occupy in Java?
If that's the case I'm not sure, sorry.
A a1;
All the above does is define a local variable on the execution stack so no heap memory is reserved.
Enough to store a reference to any A! :-)
Note that it's generally impossible to know exactly how many bytes a particular implementation will actually use for a particular allocation, even in low-level languages like C: malloc() itself is a function which obviously needs to maintain internal data structures. To avoid fragmentation, it usually allocates a 2^n-sized block of memory. And so on.
If you're concerned about how much memory is actually used, write a sample program, and run it through your profiler.
As has been mentioned, it will use either 32-bits or 64-bits, however if the reference is only placed in a register, it might not use any memory.
reference variable occupies bytes which are solely dependent on arhitecture of jvm (8 bytes for 64 bits and 4 for 32 bi
A a1; allocates on the stack, not the heap.
However, this is all up to implementation, and is not actually defined, as far as I know.
Even for the amount of memory in the stack, that will depend of what is contained/defined in A.
null does not occupy any space in memory.
Simply saying int occupies some bytes like float occupies some space in memory.
But for null no space is occupied in memory.
Send me details if my answer is wrong.
Try for system.memorrysize() like method in Java.

Categories