1

learning C here. I am currently in topic of pointers and i am confused about somethings.

int c;
printf("insert the first number of your age");
scanf("%d", &c);

The one above works ok but not

int c;
int p = 1;
c = &p;

And also, why don't we use & for strings. As in for example

char val[2];
printf("please insert your Blood type");
scanf("%c",val);

I have a decent knowledge of computer architecture. If it can be related, it would be very nice if you explain it to me by connecting it to microinstructions and the CDU(control decoding unit) by relating it also to external buses like MAR and MDR

Ted Lyngmo
  • 93,841
  • 5
  • 60
  • 108
  • 4
    Did you mean `int *c;`? And what does `p` do in the second snippet? – HolyBlackCat Jul 05 '23 at 17:23
  • edited @HolyBlackCat – Bitwoded S.Demissie Jul 05 '23 at 17:25
  • A "string" is **already** a pointer to a null-terminated array of characters. I don't think you want `scanf("%c",....)` but then I don't think you should be using `scanf` at all. :) – tchrist Jul 05 '23 at 17:30
  • when one uses pointers, there are at least two memory locations to consider. The location of the variable pointed by the pointer and the location of the pointer itself. int c; int p = 1; c = &p; (does not work because of the fact that &p returns the adress of the variable p but assigned variable c is not a pointer. If c were to defined as int *c; this would work. (Because c would be a pointer which is capable of holding a memory adress to point to a variable) --- [the pointer itself is a variable, so another pointer could be created to point to the pointer] – Ahmet M Jul 05 '23 at 17:32
  • 3
    @tchrist -- careful not to confuse learners: a string is a null-terminated array of characters, and so is a string literal. It is true that arrays (including string literals) decay to pointers to their first elements (in most expressions), but mixing up pointers and arrays seems to be one of the most common mistakes for learners and causes many problems. – ad absurdum Jul 05 '23 at 17:36
  • All of the software running on a computer is implemented using the instruction set of that computer (instruction set = computer architecture). Hence, computers provide an abstraction for the software layer so that programmers should not be have to think about specific hardware implementations. In other words, there could be many implementations for an architecture and that implementation change would not affect the software in terms of functionality. (it would affect performance) ). The instructions given are matted to the instruction in the instruction set architecture by the compiler. – Ahmet M Jul 05 '23 at 17:41
  • For instance, There is an instruction in MIPS to read a word from memory to a register. lw $s2, 0($s1). In here lw stands for load a word and $s2 is where the word is loaded (which is register in mips) $s1 would be the register which holds an adress value. 0 added to that adress to find where the word is at in the memory. In this example, $s1 would be the value contained in the pointer memory adress and $s2 would the value to be written to the variable pointed by that pointer) – Ahmet M Jul 05 '23 at 17:43
  • If you were to use assembly language (computer instruction set architecture) directly, you could write an address to any register and any where in the memory. However, when you use a programming language, it will constrain you to raise your productivity and decrease the likelihood of bugs). One of those constrains in C programming language is that an address could be assigned to a pointer with the same type as the value in that address. (This a very basic and useful thing) – Ahmet M Jul 05 '23 at 17:51
  • @adabsurdum You're right: it's easily confused, and always has been. – tchrist Jul 05 '23 at 17:54
  • I don't think you need to get as low level as MAR/MDR in a toy CPU. Just assembly language is usually more than fine to see loads and stores. (Make sure to enable optimization, otherwise there will be a mess of loads and stores of locals to the stack between statements. See [How to remove "noise" from GCC/clang assembly output?](https://stackoverflow.com/q/38552116) for how to write functions that compile to something interesting to look at. It could be useful to use `volatile` on some variables to make sure accesses to them are visible in the asm.) – Peter Cordes Jul 05 '23 at 18:29
  • ARM or MIPS might be good choices since they have obvious `ldr` / `str` or `lw` / `sw` instructions, instead of just memory vs. register operand for x86 `mov`. https://godbolt.org/ has compilers for all of those ISAs. – Peter Cordes Jul 05 '23 at 18:30

2 Answers2

3
  • In scanf("%d", &c); you pass a pointer to int to the scanf function so that it can write into the memory of the variable the pointer is pointing at (that is, c).

  • In c = &p; you try to assign an int* to an int. These are incompatible types. An int* points at an int, but isn't an int.

  • In scanf("%c",val); the char array val decays into a pointer to the first element in the array. The type is a char* - which is exactly what %c requires to write a char into the memory provided. Had the variable var been a char instead of an array of char, you would have needed scanf("%c", &val); to provide a char*.

it would be very nice if you explain it to me by connecting it to microinstructions and the CDU(control decoding unit) by relating it also to external buses like MAR and MDR

I don't see the relevance. You are using a language that provides a set of rules and abstractions from what goes on underneath. The scanf and pointer operations described works the same way in any conforming C implementation regardless of what machine code, micro instructions and buses that is required for the C code to work on the specific target platform. Also, I know very little about those things.

Ted Lyngmo
  • 93,841
  • 5
  • 60
  • 108
1
int c;
int p = 1;
c = &p;

c is not a pointer, so it cannot hold the address of p. Should you have used instead:

int *c;
int p = 1;
c = &p;

then the code would have been correct. But it's not clear from the context what you pretend to do with those variables, so I'm just guessing.

Luis Colorado
  • 10,974
  • 1
  • 16
  • 31