Question: I want to declare a pointer, have it hold a custom address and then assign a value to it: 

```
void main()
{
    char *ptr;
    ptr = (char *)0x123123; //the assignment works perfectly with a cast
    printf("%p\n", ptr); //and the pointer indeed holds the address it's supposed to
    *ptr = 'a'; //but this breaks
    puts("2");
}

```

Initially I thought the reason is because I'm trying to dereference uninitialized memory. But I doubt actually that this is the case, since this `some_type *some_ptr = &some_variable;` works flawlessly, so the deal must be the address I assign it to. 

Then I thought, in the same way `3` or `'a'` or `"alpine"` are constants, `(char *) 0x123123` must be a constant too. And `const`-s can't be edited in C, but that still can't be it, because an attempt to change a `const` value will not compile. 

3rd assumption would be that such an address must be unavailable, but this doesn't make sense either, because line 4 works always, no matter the address I give or the type of the `pointer`.

Answer: 
> 
> 3rd assumption would be that such an address must be unavailable,
> 
> 
> 

That is correct: on modern OSes (which all have memory protection) you can't write to arbitrary memory address.

It used to be possible to access any memory on OSes that didn't utilize virtual memory (such as `MS-DOS`), but allowing that is generally a *very bad idea* -- it allowed random program to corrupt OS state, and required very frequent reboots.

> 
> but this doesn't make sense either, because line 4 works always, no matter the address I give or the type of the pointer.
> 
> 
> 

You confuse two distinct operations: *printing* an address (allowed no matter what that address is) and *dereferencing* an address, i.e. reading or modifying the value stored *at* the address (only allowed for valid addresses).

The distinction is similar to "can you print an address?" (e.g. "123 Main Street, SomeTown, SomeCountry"), and "can you enter a house at that address?" (not possible for above address because there is no "SomeCountry" on Earth). Even if the address is valid, e.g. "1600 Pennsylvania Ave NW, Washington, DC 20500", you may still not be allowed to enter it.
The OP clarified elsewhere, that this is actually an XY problem.

The X problem: reading/writing to arbitrary memory locations.

The Y problem: implementing a linked list that uses consecutive memory.

Of course, the answer to that is: one has to implement his complete own memory management system to get there. 

As in: first, you use `malloc()` to acquire a large block of consecutive memory. Then you can use *arbitrary* pointers **within** that block of memory. But of course, *your* code has to track which addresses are already used. Or to correctly "free" up when list nodes get deleted.

The tricky part is about handling the corner cases, such as: what happens when your last "pointer" gets used up? Do you malloc() a larger area, and **move** all data in memory? 

Finally: assume that you don't manage a block of memory, but a single array. ( linked lists implementations are often based on arrays, as that makes some things much easier )