nostackframe simply prevents the compiler from managing local variables for you (including "invisible" temporaries). If you try to declare local variables in a
nostackframe procedure, you'll get an error.
In older x86 (32-bit) calling conventions, all arguments were pushed onto the stack like you described, but that is no longer the case: all major modern calling conventions (x86-64) pass the first few parameters in registers (Windows uses
rcx, rdx, r8, r9 while Linux uses
rdi, rsi, rdx, rcx, r8, r9). This improves performance, but it also means that parameters must be manually stored somewhere in non-leaf functions (aka functions that call other functions, like your example).
@ALLIGATOR's response is what you need to do - manually allocate & deallocate stack space by moving the stack pointer (if you decide to add more parameters you must pay attention to
stack alignment, though).