2

I am learning programming for 8 bit 6502 in C compiler (www.cc65.org)

The NES FC has a 8bit 6502 processor and a 2K RAM. However, the following C compiles (into a nes file) and loads successfully in VirtualNES emulator.

#include "conio.h"
#include "stdlib.h"

int dump[1000];

void main()
{
    int *a;
    a = (int*)malloc(19222999);
    cputs("Hello, World!");
    a[0] = 1;
    for(;;); // loop forever, never ends
}

Why this is OK ? clearly I have allocated more memory than 2K in the above C code.

justyy
  • 5,831
  • 4
  • 40
  • 73
  • 1
    [Please don't cast the return value of `malloc()` in C](http://stackoverflow.com/a/605858/28169). – unwind Nov 25 '13 at 15:52
  • For the record the default CC65 NES set-up/linker script relies on an 8 kB RAM expansion (an extra memory chip on the cart, basically.) Otherwise your 1000 integer array would not have fit into 2048 bytes of RAM as the runtime needs space for other things as well. Oh, and I would strongly suggest that you avoid this type of dynamic memory allocation on the NES, else you'll run into trouble with fragmentation. – doynax Nov 25 '13 at 16:14
  • @doynax Full ack. On embedded system, it is best to restrict usages of `malloc()` to short-lived, small memory blocks and maybe to memory blocks where I need "all remaining RAM" where I calculate the amount of memory to allocate from parameters of memory allocation which are available to me from the linker or so. – glglgl Nov 25 '13 at 16:17

2 Answers2

7

Segfaults are a wonderful, miraculous boon of the modern age; they represent our computers self-diagnosing their own bugs, moment-to-moment.

In olden times, in contrast, there was very little way to "crash" a computer, in the sense that the computer would have some awareness that something had gone wrong, causing it to do something else instead. Here, you've written a 1 to somewhere in memory (quite possibly overwriting something important!), and then the computer goes on.

The takeaway: In old architectures and embedded systems, "doesn't crash" is a very low bar to clear, and does not indicate that things are OK.

Sneftel
  • 40,271
  • 12
  • 71
  • 104
3

You don't check the value of a. (BTW, why do you cast the return value?)

I suppose it is NULL. So a write access to a[0] is no valid C, but it might (depending on the architecture) work nevertheless - and cause havoc and disruption there.

The compiling process works as expected, because for the compiler and the linker, malloc() is a function as anything else. The mistake only happens at runtime.

glglgl
  • 89,107
  • 13
  • 149
  • 217