Computer Programming. Pointers. Marius Minea. 20 November 2017

Similar documents
Computer Security. Robust and secure programming in C. Marius Minea. 12 October 2017

C: Pointers, Arrays, and strings. Department of Computer Science College of Engineering Boise State University. August 25, /36

Why Pointers. Pointers. Pointer Declaration. Two Pointer Operators. What Are Pointers? Memory address POINTERVariable Contents ...

Pointers. 10/5/07 Pointers 1

Administrivia. Introduction to Computer Systems. Pointers, cont. Pointer example, again POINTERS. Project 2 posted, due October 6

C: Pointers. C: Pointers. Department of Computer Science College of Engineering Boise State University. September 11, /21

by Pearson Education, Inc. All Rights Reserved.

Arrays and Pointers. CSE 2031 Fall November 11, 2013

Arrays and Pointers in C. Alan L. Cox

Contents of Lecture 3

Arrays and Pointers. Arrays. Arrays: Example. Arrays: Definition and Access. Arrays Stored in Memory. Initialization. EECS 2031 Fall 2014.

CS 241 Data Organization Pointers and Arrays

Arrays. An array is a collection of several elements of the same type. An array variable is declared as array name[size]

Week 5 9 April 2018 NWEN 241 More on pointers. Alvin Valera. School of Engineering and Computer Science Victoria University of Wellington

CS 0449 Sample Midterm

C Review. MaxMSP Developers Workshop Summer 2009 CNMAT

CSCI-243 Exam 1 Review February 22, 2015 Presented by the RIT Computer Science Community

Arrays and Strings. Antonio Carzaniga. February 23, Faculty of Informatics Università della Svizzera italiana Antonio Carzaniga

Goals of this Lecture

Fundamental of Programming (C)

Arrays, Strings, & Pointers

First of all, it is a variable, just like other variables you studied

CS 261 Fall Mike Lam, Professor. Structs and I/O

Computers Programming Course 6. Iulian Năstac

Pointers. Pointer References

CS 61c: Great Ideas in Computer Architecture

Memory, Arrays & Pointers

A brief introduction to C programming for Java programmers

Agenda. Components of a Computer. Computer Memory Type Name Addr Value. Pointer Type. Pointers. CS 61C: Great Ideas in Computer Architecture

C BOOTCAMP DAY 2. CS3600, Northeastern University. Alan Mislove. Slides adapted from Anandha Gopalan s CS132 course at Univ.

Pointer Basics. Lecture 13 COP 3014 Spring March 28, 2018

Jagannath Institute of Management Sciences Lajpat Nagar. BCA II Sem. C Programming

CS 61C: Great Ideas in Computer Architecture. Lecture 3: Pointers. Krste Asanović & Randy Katz

C++ Programming Chapter 7 Pointers

Dynamic Allocation in C

Dynamic Allocation in C

SYSC 2006 C Winter 2012

Data Types and Computer Storage Arrays and Pointers. K&R, chapter 5

Systems Programming and Computer Architecture ( )

Arrays, Strings, and Pointers

Memory Corruption 101 From Primitives to Exploit

Dynamic memory allocation

Other C materials before pointer Common library functions [Appendix of K&R] 2D array, string manipulations. <stdlib.

Dynamic memory allocation (malloc)

CS 61C: Great Ideas in Computer Architecture. C Arrays, Strings, More Pointers

Pointers. Pointers. Pointers (cont) CS 217

Character Strings. String-copy Example

Operating Systems 2INC0 C course Pointer Advanced. Dr. Ir. Ion Barosan

COMP 2355 Introduction to Systems Programming

CS 61C: Great Ideas in Computer Architecture. Lecture 3: Pointers. Bernhard Boser & Randy Katz

Understanding Pointers

Computer Programming: Skills & Concepts (CP) Strings

Pointers, Arrays, and Strings. CS449 Spring 2016

[0569] p 0318 garbage

Intermediate Programming, Spring 2017*

C Language Part 1 Digital Computer Concept and Practice Copyright 2012 by Jaejin Lee

Lecture 04 Introduction to pointers

... Lecture 12. Pointers

Arrays, Strings, and Pointers

Hacking in C. Pointers. Radboud University, Nijmegen, The Netherlands. Spring 2019

A Quick Introduction to C Programming

C++ for Java Programmers

ch = argv[i][++j]; /* why does ++j but j++ does not? */

Agenda. Peer Instruction Question 1. Peer Instruction Answer 1. Peer Instruction Question 2 6/22/2011

Lecture07: Strings, Variable Scope, Memory Model 4/8/2013

Outline. Computer Memory Structure Addressing Concept Introduction to Pointer Pointer Manipulation Summary

Array Initialization

C Characters and Strings

Chapter 16. Pointers and Arrays. Address vs. Value. Another Need for Addresses

Procedural programming with C

COMP26120: Pointers in C (2018/19) Lucas Cordeiro

Arrays, Strings, and Pointers

Memory and Addresses. Pointers in C. Memory is just a sequence of byte-sized storage devices.

Pointers as Arguments

ECEN 449 Microprocessor System Design. Review of C Programming. Texas A&M University

Pointers and Memory Management

Course organization. Course introduction ( Week 1)

Agenda. The main body and cout. Fundamental data types. Declarations and definitions. Control structures

Advanced Pointer Topics

Arrays and Memory Management

8. Characters, Strings and Files

PIC 10A Pointers, Arrays, and Dynamic Memory Allocation. Ernest Ryu UCLA Mathematics

Language comparison. C has pointers. Java has references. C++ has pointers and references

CS107 Handout 08 Spring 2007 April 9, 2007 The Ins and Outs of C Arrays

High Performance Programming Programming in C part 1

COMP 2355 Introduction to Systems Programming

Pointers (part 1) What are pointers? EECS We have seen pointers before. scanf( %f, &inches );! 25 September 2017

K. N. King: chapters 8 and 12

CSCI 171 Chapter Outlines

I2204 ImperativeProgramming Semester: 1 Academic Year: 2018/2019 Credits: 5 Dr Antoun Yaacoub

18-642: Code Style for Compilers

From Java to C. Thanks to Randal E. Bryant and David R. O'Hallaron (Carnegie-Mellon University) for providing the basis for these slides

The C Programming Language Part 4. (with material from Dr. Bin Ren, William & Mary Computer Science, and

Pointers (continued), arrays and strings

Programming. Pointers, Multi-dimensional Arrays and Memory Management

Outline. Lecture 1 C primer What we will cover. If-statements and blocks in Python and C. Operators in Python and C

CSE 565 Computer Security Fall 2018

Lecture 2: C Programm

Code: analysis, bugs, and security

QUIZ. 1. Explain the meaning of the angle brackets in the declaration of v below:

Transcription:

Computer Programming Pointers Marius Minea marius@cs.upt.ro 20 November 2017

Pointers are addresses Any lvalue (variable x, array element, structure field) of type T has an address &x of type T * where its value is stored. An array name is its address A string is represented by its address, it is a char * Valid addresses are non-null. NULL indicates an invalid address NULL is (void *)0 i.e., 0 cast to type void * An address is a numeric value, but not of type int or unsigned. It may be printed with format specifier "%p" in printf. For low-level systems programming: Types intptr_t and uintptr_t (from stdint.h) are the right size to hold a void *.

Pointers are used like everything else We need to know how to 1. declare a variabile of pointer (address) type 2. obtain a pointer (address) value 3. use a pointer (address) value To use pointers correctly, need to (like for all variables/values): 1. be aware of their type 2. initialize them correctly 3. use the right operators / functions

Declaring pointers Declaring pointers: type *ptrvar; the variable ptrvar may contain the address of a value of type Examples: char *s; int *p; When declaring several pointers, need * for each of them: int *p, *q; two integer pointers int *p, q; one pointer p and one integer q Initialize pointers in declarations wherever possible like with any variable: don t risk using uninitialized values

Initialization and assignment Obtaining pointer values: From an array name (a pointer): int tab[10], *a = tab; same as: int tab[10]; int *a; a = tab; Declaring T tab[n]; array name tab has type T * Taking the address & of a variable: int n, *p = &n; same as: int n; int *p; p = &n; A string constant is a pointer to the contents (to first char): char *s = "test"; same as: char *s; s = "test";

Dereferencing a pointer The dereferencing (indirection) operator * *p gives the object located at address p prefix operator operand: pointer (address); result: object (variable) indicated by pointer *p is an lvalue (can be assigned, like a variable) can also be used in an expression, like any value of that type Declaration syntax suggests types! T *p; says T * is the type of p and T is the type of *p

Address and dereference operators are opposites The operator * is the inverse of & *&x is the object at the address of x, that is, x &*p is the address of the object at address p, that is, p int x, y, *p = &x; y = *p; /*y = x */*p = y; //x = y Always check the types! x has type T &x has type T * p has type T * *p has type T

We can have pointers to pointers to pointers... Any variable has an address pointer variables have addresses Any expression has a type: The address of a variable of type T has type T * The address of a variable of type T* has type T ** etc. Having declared int *p; the type of &p is int ** we can declare int **p2 and initialize/assign it with &p declaration T * p; may be read: T * p; p has type T * T *p; *p has type T char **s; address of char addr char *t[8]; array of 8 char addr Variable Value Address int x = 5; 5 0x408... int *p=&x; 0x408 0x51C... int **p2=&p; 0x51C 0x9D0

Initialization and assignment are different! WARNING: A declaration with initializer is NOT an assignment! The * in a declaration is NOT an indirection operator! * is written next to the declared variable, but belongs to the type! Declaration int *p; suggests that *p is an int but the variable declared is p, NOT *p (*p is not an identifier) so the initializer is for p, NOT for *p. int t[2] = { 3, 5 }; initializes t. WRONG: t[2] = { 3, 5 }; int x, *p = &x; is like int x; int *p; p = &x; (p is initialized/assigned, NOT *p). *p = &x is a type error! char *p = "str"; is char *p; p = "str"; WRONG: *p = "str";

Pointers hold only addresses, not data! Programs can t have just pointers. These must point to something (useful data: need variables to store it in). Understand what each declaration means! Declaring int x; means I want to have an integer. What for? What value does it have? Better: int min = a[0]; //start with first element Declaring char *p; only means I want to use the address of a char DON T KNOW WHAT ADDRESS. VARIABLE p UNINITIALIZED. NO CHARS DECLARED YET. NO ROOM TO STORE THEM. Need: char *p = buf; p points to array char buf[10]; declared before char *p = "ana are mere"; p points to a string constant char *p = strchr(buf, < ); returned by function, could be NULL

ERROR: no initialization It s an ERROR to use any uninitialized variable int sum; for (i=0; i++ < 10; ) sum += a[i]; // initially?? program behavior is undefined (best case: random initial value) Pointers must be initialized before use, like any variables with a valid address (of a variable), or an initialized pointer with a dynamically allocated address (later) ERROR: int *p; *p = 0; ERROR: char *p; scanf("%20s", p); p is uninitialized (best case NULL, if global variable) value will be written to unknown memory address memory corruption, security vulnerability; program crash is luckiest case! WARNING: a pointer is not an int. WRONG: int *p = 640;! Address space is determined by system, not user CANNOT choose an arbitrary address we want

Using pointer parameters: assignment in functions A function CANNOT change a variable passed as parameter because the value is passed, not the variable itself void nochange(int x) { ++x; printf("%d\n", x); } void try(void) { int a = 5; nochange(a); // nochange prints 6 printf("%d\n", a); // main still prints 5! } But, with a variable s address p, we may use its value:...= *p; assign it: *p =...; Having a variable s address, a function may write to it (e.g. scanf). void swap (int *pa, int *pb) { // swaps values at 2 addresses int tmp; // keeps first changed value tmp = *pa; *pa = *pb; *pb = tmp; // integer assignments }... int x = 3, y = 5; swap(&x, &y); // now x = 5, y = 3}

Pointers as function parameters We use addresses as function parameters: to pass arrays (can t pass array contents in C) to return several values (return allows only one) e.g. min and max of an array; result and error code Arrays as function parameters When passing an array to a function, the address is passed The name of the array represents its address in T tab[len]; the array name tab has type T * int f(int a[]) is same as int f(int *a)

Formatted processing/printing of strings Variants of printf/scanf with strings as source/destination int sprintf(char *s, const char *format,...); int sscanf(const char *s, const char *format,...); sprintf has no limitation may overflow buffer. Use instead: int snprintf(char *str, size_t size, const char *format,...); writing is limited to size chars including \0 safe option

Converting strings to numbers int n; char s[] = "-102 56 42"; if (sscanf(s, "%d", &n) == 1)... //number OK (but we don t know where processing of string stopped) long int strtol(const char *s, char **endptr, int base); assigns to *endptr the address of first unprocessed char (if not needed, pass 2nd arg. NULL) if base is 0, accepts octal/decimal/hex (as in C, like %i in scanf) char *end; long n = strtol(s, &end, 10); //upto base 36 also strtoul for unsigned long, strtod for base 10 double int n = atoi(s); returns 0 on error, but also for "0" use only when string known to be good

Command line arguments command line: program name with arguments (options, files, etc.) Examples: gcc -Wall prog.c or ls directory or cp file1 file2 main can access command line if declared with 2 args (only these): int argc count of words in command line (1 + arguments) char *argv[] arguments: array of strings, ends with NULL #include <stdio.h> int main(int argc, char *argv[]) { // same as char **argv printf("program name: %s\n", argv[0]); if (argc == 1) puts("program called with no arguments"); else for (int i = 1; i < argc; i++) printf("argument %d: %s\n", i, argv[i]); return 0; } // run:./a.out somestring anotherstring thirdstring etc Run a command from program: int system(const char *cmdline);

Pointer do s and dont s (recap) *p is NOT a pointer! unless p is char **, int **, etc. p is the pointer. *p is the object/value at address p Programs work with data. Pointers are addresses, they only point to data. Don t declare a pointer unless you have what it should point to. except: dynamic allocation (provides pointer and data space) char *p = &s[i]; char *p = "test"; char *p = argv[0]; if array char s[40]; declared before data is constant string data put there by runtime system Declare data and pass address for function to fill in data: int n; if (scanf("%d", &n) == 1)... char *end; double d = strtod(s, &end); int x, y; swap(&x, &y);

Arrays and pointers Declaring an array allocates a memory block for its elements The array s name is the address of that block (of first element) &a[0] is same as a and a[0] is same as *a Can declare T a[len], *pa; and assign pa = a; Similar: a and pa have same type: T* But: pa is a variable uses memory; can assign pa = addr a is a constant (array has fixed address) can t assign a = addr a a[0] a[1] a[2] a[3] a[4] a[5] pa... 5C0 address (hex) int a[6]; int *pa = a; 5C0 5D0 5E0 *a and *pa: indirections with different operations in machine code: *a references object from constant address (direct addressing) *pa must first get value of variable pa, loading it from &pa, then dereference it (indirect addressing)

Arrays and pointers (cont d) Array: char s[] = "test"; s[0] is t, s[4] is \0 etc. s is a constant address (char *), not a variable in memory CANNOT assign s =... but may assign s[0] = f sizeof(s) is 5 * sizeof(char) &s is s but type is address of 5-char array: char (*)[5] sizeof (entire array) is not strlen (up to \0 ) Pointer: char *p = "test"; p[0] is t, p[4] is \0 (same) p is a variable of address type (char *), has a memory location CANNOT assign p[0] = f ("test" is a string constant) can assign p = s; then p[0] = f ; can assign p = "ana"; sizeof(p) is sizeof(char *) &p is NOT p WRONG: scanf("%4s", &p); RIGHT: scanf("%4s", p); (if p is valid address and has room)

Pointer arithmetic pointer + int = pointer (of same type) A variable v of type T uses sizeof(t) bytes &v + 1 is the address after v s space (next object) &v + 1 is value of &v plus sizeof(t) bytes + on a pointer increments by object size (not one byte)

Pointer arithmetic: add 1. Add/subtract pointer and integer: like address of array element a + i means &a[i] *(a + i) means a[i] 3[a] is a[3] a + i means i elements past a, NOT i bytes past a for char *a 1 element = 1 byte number also means bytes increment ++a, a++: a becomes a+1 before/after evaluation Pointer arithmetic is only valid within the same array/object exception: can take address just beyond (at end) of array int a[len], *end = a + LEN; a+len+1 is not a valid address (beyond legal memory access) WARNING! C has no overflow checks! Careful with indices!

Pointer arithmetic: difference 2. Difference: only for pointers of same type (and in same array!) = number of objects of type T between the two addresses &a[j] - &a[i] == j - i To get the number of bytes, (cast) pointers to char * p - q == ((char *)p - (char *)q) / sizeof(t) No other arithmetic operations between pointers are defined! May use comparison operators: ==,!=, <, etc. comparing order <, <= etc. only allowed within same structure (relative memory placement of different objects is irrelevant)

No pointer arithmetic with void * void * = pointer of unspecified type don t know type of object can t dereference, can t do arithmetic But: void * are assignment-compatible with any pointer Useful for writing functions that accept any pointer Cast void * to char * to do arithmetic: void setzero(void *a, unsigned cnt, unsigned size) { for (char *p = (char *)a + cnt * size; --p >= a; ) *p = \0 ; }

Pointer arithmetic and operator precedence ++ (and --) have higher precedence than * (indirection) Increment pointer *p++ ++ applies to p: take value, (post)increment pointer value is object at original pointer value *++p increments pointer, then dereferences value is next object after original pointer value Increment value at pointer (*p)++ (post)increments the value at address p expression has the value before increment ++*p (pre)increments value at address p expression has the value after increment

Pointers and indices same meaning: to indicate = to point to To write a[i], need two variables and one addition (base + offset) and multiplication with size of type (if not char, of size 1) Simpler: directly with pointer to element &a[i] (a+i) increment pointer rather than index when traversing array char *strchr_i(const char *s, int c) { // search char in s for (int i = 0; s[i]; ++i) // traverse string up to \0 if (s[i] == c) return s + i; // found: return address return NULL; // not found } char *strchr_p(const char *s, int c) { for ( ;*s; ++s) // use parameter for traversal if (*s == c) return s; // s points to current char return NULL; // not found }

Pointers and indices (cont d) char *strcat_i(char *dest, const char *src) { int i = 0, j; while (dest[i]) ++i; for (j = 0; src[j]; ++j) dest[i+j] = src[j]; dest[i+j] = \0 ; return dest; } char *strcat_p(char *dest, const char *src) { char *d = dest; // need to save dest for return while (*d) ++d; while (*d++ = *src++); // string copy return dest; }

Pointers and multidimensional arrays A bidimensional array (matrix) is declared as for instance int a[dim1][dim2]; type a[dim1][dim2]; a[i] is constant address (int *) of an array of DIM2 elements (line of the matrix) a[i][j] is j th element in array a[i] of DIM2 elements &a[i][j] or a[i]+j is DIM2*i+j elements after address a function with array parameter needs all dimensions except first must declare as sometype f(int t[][dim2]); a[i] which is *(a+i) means i lines ( DIM2 elements) after a[0] a has type int (*)[DIM2] (pointer to array of DIM2 ints)

Matrix vs. array of pointers char t[12][4]={"jan",...,"dec"}; char *p[12]={"jan",...,"dec";} t is matrix (2-D char array) p is array of pointers j a n \0 f e b \0... d e c \0 t uses 12 * 4 bytes 0x460 j a n \0 0x5C4 f e b \0... 0x9FC d e c \0 p uses 12*sizeof(char *) bytes (+ 12*4 bytes for the string constants) t[6] =... is WRONG p[6]="july" changes an address t[6] is constant address of line 7 (element 7 from pointer array p) can do strcpy(t[6],...) or strncpy

Indices or pointers: use sensibly Declare in for loop header whenever possible (since C99) enforces scope, visually clear, avoids affecting other loops Use whatever results in simpler, understandable code void matmul_i(unsigned m, unsigned n, unsigned p, double a[m][n] double b[n][p], double c[m][p]) { for (int i = 0; i < m; ++i) for (int j = 0; j < p; ++j) { c[i][j] = 0; for (int k = 0; k < n; ++k) c[i][j] += a[i][k]*b[k][j]; } } void matmul_p(unsigned m, unsigned n, unsigned p, double a[m][n] double b[n][p], double c[m][p]) { for (double *lp = a[0], *dp=c[0], *end = a[m]; lp<end; lp+=n) for (int j = 0; j < p; ++j, ++dp) { *dp = 0; for (int k = 0; k < n; ++k) *dp += lp[k]*b[k][j]; } }

Type casts and typedef Type cast is a unary operator, written as (type-name)expression the value of expression is converted to the type type-name convert int to real dereference a void * read bits of float as an int: (double)sum/cnt //force real division *(char *)p //char at address p *(uint32_t *)&f typedef is a keyword used to define a new name for a type Syntax: typedef declaration the identifier that would have been a variable in the declaration becomes a type name typedef uint16_t u16; // u16 is synonym for type uint16_t // with just: uint16_t u16; it would be a variable typedef char line[80]; // line: type for array of 80 chars // with just: char line[80]; it would be an array line text[100]; //text is array of 100 lines

Function pointers A function name is its address (a pointer) like for arrays We can declare pointers of function type. Compare: int f(void); int (*p)(void); declare function: declare function pointer: Can assign pfct = fct declares a function returning int declares pointer to function returning int restype fct (type1,..., typen); restype (*pfct) (type1,..., typen); with the name of an existing function CAUTION! Need parantheses for (*pointer), otherwise: int *fct(void); declares a function returning pointer to int Function name is pointer can call function using pointer #include <math.h> // Example: f is a function parameter void printvals(double (*f)(double)) { // arg.of f not named for (int i=0; i<10; ++i) printf("%f\n", f(.1*i)); } int main(void) { printvals(sin); printvals(cos); return 0; }

Using function pointers stdlib.h: binary search for key in sorted array; and quicksort void *bsearch(const void *key, const void *base, size_t nmemb, size_t size, int (*compar)(const void *, const void *)); void qsort(void *base, size_t num, size_t size, int (*compar)(const void *, const void *)); address of array to sort, element count and size address of comparison function, returns int <, = or > 0) has void * arguments, compatible with pointers of any type typedef int (*comp_t)(const void *, const void *); // cmp fun int intcmp(int *p1, int *p2) { return *p1 - *p2; } int tab[5] = { -6, 3, 2, -4, 0 }; // array to sort qsort(tab, 5, sizeof(int), (comp_t)intcmp); // sort ascending Can also declare function with void *, do cast in function int intcmp(const void *p1, const void *p2) { return *(int *)p1 - *(int *)p2; } qsort(tab, 5, sizeof(int), intcmp); // no cast, has right type

When to use pointers? When the language forces us to: arrays (memory blocks) cannot be passed / returned from functions only their address (array name is its address) addresses carry no size information must pass size parameter strings: a string (constant or not) is a char * need not pass size, since null-terminated functions: a function name is its address When a function needs to modify variable passed from outside pass address of variable WARNING! Any address passed to a function needs to be valid (point to allocated memory) functions use their arguments pointers must be valid