Homework • HW6 On line – due next class • Starting K&R Chapter 7 and Appendix B • Also, UNIX – Various chapters in Glass 1 Standard Library Functions • Learn as much as possible about all standard library functions K&R Appendix B • On line, you can get documentation about standard library functions with man command % man printf • For more information, use grep on standard library function names in standard .h files % grep strcmp /usr/include/* 2 UNIX grep, Glass Pg 219+ • UNIX command “grep” finds matches for a specified string in identified filenames • If no filenames present, grep searches stdin • Some options in grep: -i -n -v -w ignore case (“TEXT” same as “text”) adds line numbers to display gives only lines that don’t match only matches complete words 3 UNIX “Pipes”, Glass Pg 84+ • Remember redirection for stdin and stdout? % command <filename1 >filename2 • In general, you can invoke a program and pass stdout from that program as stdin to another program via UNIX pipe – symbol | % command1 arguments | command2 arguments % grep pattern filename(s) | more 4 Standard Input /Output, 7.1 • C code for reading stdin char getchar (void) gets a character from stdin • C code for writing to stdout void putchar(char) puts a character to stdout • stdin and stdout can be redirected or piped % ./tail <tail.in | more % cat tail.in | ./tail >filename2 5 Formatted Output, printf, K&R 7.2 • Formats and prints out internal values. int printf(char *format, arg1, arg2, . . .); • printf has a variable length argument list (as many arguments after the first one as % conversions in the format string) • We will learn how to do this shortly • Return from printf is number of characters printed • Haven't used this up till now, but it may be useful if there is some error or limit truncation 6 Formatted Output, printf • Between the % and the conversion character, there are a number of other characters which may exist. In the order they must be placed, they are: - (minus sign) + (plus sign) 0 (zero) m (number m) . (dot) p (integer p) h or l (letters) left adjust printing of argument print with a leading sign character pad with leading zeros instead of spaces minimum field width separates min field width & precision precision: max chars for string min digits for int h for short int, l for long int • ORDER for %d is: %[-][+][0][m][.][p][h|l]d, Note: No embedded spaces allowed! 7 Formatted Output, printf • Figure out what these would do: %10d, %-10d, %hd, %e, %10ld, %10.p • Experiment for 10 minutes with a program, using different formats • Learn string precision given on pg. 154 • Also, to print at most max characters from string s (max is int type var or const), use * after % and include the int max as an argument before s: printf("%.*s", max, s); 8 Formatted Output, printf • Can print string literal as format string with no “%s” printf("hello, world!\n"); • Could also print a string variable as format string: char s[ ] = "hello, world"; printf(s); • If string s has a % character in it, this is unsafe! • printf will look for another argument after format string s. Better to write out a variable string s as: printf("%s", s); 9 Formatted Output, sprintf • See sprintf in K&R Appendix B, pg 245 • Function sprintf works same as printf, but it writes to a specified string, e.g. char array[ ], with trailing ‘\0’ int sprintf(char *string, char *format, arg1, arg2, …); • Note: int return value does not include trailing ‘\0’ • Recall how we wrote itoa() and itox() functions • No functions like this in C library! • Use sprintf() to print int into a string using %d or %x 10 Formatted Input, scanf • This is the opposite of printf. Reads in variables from stdin using conversion format string. See pg. 246 (and prior pg 245 which explains everything). int scanf(char *format, …); • Return value from scanf( ) is number of successfully scanned tokens • Not successful if scanf can't parse any value brought in from stdin according to the specified format 11 Formatted Input, scanf • Must call scanf with a POINTER to each variable so that values can be set by scanf which is a function! int age, weight; char lname[100]; while(some condition) { printf("Input your last name, age, and weight”); cnt = scanf("%s %d %d", lname, &age, &weight); } • Note: lname is an array and is already a pointer 12 Formatted Input, scanf • Scanf is useful to allow you to read in int or double value AS A NUMBER (instead of a character string leaving you to do your own conversion in your code) • scanf() always see a character sequence in stdin: it just does its own conversion to int or double 13 Formatted Input, scanf • However, scanf is FLAWED, because it ignores '\n' characters. • Can get very confusing if the user enters too few arguments on an input line being parsed by scanf • (Prompt) Input your last name, age, and weight: • (User input) Clinton 52 • User gets no response after carriage return. • User retries, remembers to enter weight this time • (User input) Clinton 52 200 14 Formatted Input, scanf • scanf sees Clinton 52 Clinton since the user entered carriage return is seen as white space • scanf thinks weight has bad value and returns 2 as number of successfully scanned tokens • scanf does not “consume” the token Clinton and the value of age will be uninitialized • The re-entry of Clinton 52 200 will be processed and returned after the incomplete Clinton 52 • Always check the return value from scanf! 15 Formatted Input, scanf • Use scanf only for programs needing only ONE input item, usually "quick and dirty" programs with no input checking. • Can't code defensively with scanf( ): can't count number of tokens parsed ON A LINE - scanf doesn't care about input lines • Best approach is to read a line into an array s[ ] and use "sscanf( )" to parse the arguments in line • This also allows you to try to interpret things in more than one way 16 Formatted Input, sscanf • See sscanf in K&R Appendix B, pg 246 • Function sscanf works same as scanf, but it reads from a specified string, e.g. char array[ ], with a trailing ‘\0’ int sscanf(char *string, char *format, &arg1, &arg2, …); • Recall how we wrote function atoi, axtoi to convert a decimal or hex character string s to an integer i? – Use sscanf(s, "%d", &i) for atoi – Use sscanf(s, "%x", &i) for axtoi 17 Formatted Input, scanf/sscanf • Note: with both scanf and sscanf, if you put specific characters in the format string, the functions must see exactly those specific characters in the user input cnt = sscanf(s, "%d/%d/%d", &month, &day, &year); • Expects input to look exactly like this: 07/23/96 • If not, cnt value returned by sscanf is less than 3 18 Variable Length Argument Lists • Both printf and scanf have an argument (the format string) that defines the number and type of the remaining arguments in the list • Concept similar to “Overloading” in Java • C does not support multiple declarations of the same function each with different lists • How is it supported in C? • Look at stack frame after a function call! 19 Typical Stack frame Stack Pointer After Call Decreasing Addresses Function’s Automatic Variables Return Data A e.g.PC, other r Registers, etc g 1 Code provides the location of the last fixed argument in call sequence to va_start Stack Pointer Before Call A r g 2 A r g 3 Address 0xffffffff From fixed arguments, the code must determine the number of additional arguments to access via offsets from stack pointer and va_arg can work its way back up the stack to get each argument 20 Variable Length Argument Lists • Use va_ macro package inside function with a variable length argument list to get args void foo (int n, …) /* note ellipsis … */ { va_list ap; /* variable name ap */ va_start(ap, n); /* n is last named arg */ • Now ap points just before first unnamed arg 21 Variable Length Argument Lists • Each call to va_arg( ) advances pointer ap by one argument and returns value by type: ival = va_arg(ap, int); fval = va_arg(ap, float); sval = va_arg(ap, char *); • Function must clean up before returning: va_end(ap); 22