1 / 36

Functions, Varargs, and Stack Smashing

Functions, Varargs, and Stack Smashing. Using the Stack for Good And Evil. Before You Sit Down Please Get The Handout at the Entrance This file is called mike-stacks-io-smash.ppt. In the Magical Land and of C, we never have to know about memory ever again!.

dwight
Download Presentation

Functions, Varargs, and Stack Smashing

An Image/Link below is provided (as is) to download presentation Download Policy: Content on the Website is provided to you AS IS for your information and personal use and may not be sold / licensed / shared on other websites without getting consent from its author. Content is provided to you AS IS for your information and personal use only. Download presentation by click this link. While downloading, if for some reason you are not able to download a presentation, the publisher may have deleted the file from their server. During download, if you can't get a presentation, the file might be deleted by the publisher.

E N D

Presentation Transcript


  1. Functions, Varargs, and Stack Smashing Using the Stack for Good And Evil Before You Sit Down Please Get The Handout at the Entrance This file is called mike-stacks-io-smash.ppt

  2. In the Magical Land and of C, we never have to know about memory ever again! All an illusion. And somebody has to pay for all of those people in mouse suits.

  3. Where we are going • We recall the many things that need to go onto the stack every time you call one of those teensy little functions (and 1 new thing) • We use our l33t haxzor skills to break through the stack and run malicious code • You write a function that takes any number of arguments, and learn how that even makes sense. We we also talk a little bit about I/O in general but you might want to take a close look at Chapter 18. • We’ll also be going pretty fast!

  4. What Goes On To The Stack During A Function Call? short exampleFunction(short firstParam, short secondParam) { short firstLocal; short secondLocal; static short thirdNotReallyLocal = 77; return 99; } /* EXECUTION STARTS HERE */ short result = exampleFunction(1,2); I can think of 6 different kinds of data.

  5. What Goes On The Stack • Parameters to the function • Return value of the function • Address to allow functions to return • The frame pointer • Any automatic variables you define in the function • Values of any registers you happen to clobber in your function NOT any static variables you define in the function.

  6. Using the stack pointer is annoying SP SP Local Variable X is at SP + 2 After some allocations, Local Variable X is at SP + 5

  7. The Frame Pointer points to the first local variable SP SP FP FP Local Variable X is at FP - 1 After some allocations, Local Variable X is still at FP - 1

  8. Things to Remember About the Frame Pointer • Its purpose is to give each variable a constant offset from a “known good” point of reference • On the LC-3, it’s often stored in R5 • It always points to the first local variable of a function • When you start your function, you save off the old function’s frame pointer to the stack, then set F5 to your new frame pointer

  9. Who does what? • Caller • Puts arguments onto stack (RL) • Does a JSR (or JSRR) to function • Callee • Makes space for Return Value and Return Address (and saves Return address) • makes space for and saves old FP • Makes FP point to next space • Moves SP enough for all local variables • Starts execution of "work" of function

  10. How about return? • Callee (continued) • As registers are needed their current contents can be spilled onto stack • When computation done... • Bring SP back to base • Restore FP (adjust SP) • Restore RA (adjust SP) • Leave SP pointing at return value • RET

  11. short exampleFunction(short firstParam, short secondParam) { short firstLocal; short secondLocal; static short thirdNotReallyLocal = 77; return 99; } /* EXECUTION STARTS HERE */ short result = exampleFunction(1,2); • Remember the order from the last slide. • Caller Puts arguments onto stack (RL) • Callee • Makes space for Return Value and Return Address (and saves Return address) • makes space for and saves old FP • Makes FP point to next space • Moves SP enough for all local variables

  12. Where We Are • You should be able to infer from source code what is going to be on the stack and where • Next we will use this knowledge for evil: how to exploit the structure of the stack to execute malicious code • Eventually we’ll also use it for useful things like varargs functions, but you really care more about the evil don’t you?

  13. Exploit My Code

  14. How Could Anybody Be That Dumb?

  15. gets verses fgets C provides a input function called gets which you should never use. char *gets(char *s) gets reads a line from stdin into the buffer pointed to by s until either a terminating newline or EOF, which it replaces with '\0'.

  16. fgets – bounded input char *fgets(char *s, int size, FILE *stream); • fgets() • reads in at most one less than size characters from stream • stores characters read into the buffer pointed to by s. • Stops reading after an EOF or a newline. • Stores a newline into the buffer if one is read • Stores a '\0' after the last character in the buffer. • Returns s on success and NULL on error or when end of file occurs while no characters have been read.

  17. How can I prevent these security holes? • NEVER use input/output functions that can overflow a buffer • Do not assume your input is well formed, even if it comes from someplace like a save file you’ve written • Keep it simple

  18. Where we are • You should be able to infer from source code what is going to be on the stack and where • You know how to exploit the structure of the stack to execute malicious code, and you feel fully prepared to do it in interesting ways on your homework and lab • Now we’re going to write some code using varargs. It’s crazy stack manipulation for good!

  19. Chapter 18: I/O in C I am skipping over some aspects of this chapter. I made a fancy cheat sheet for you to help. But reading the chapter might also be good.

  20. Not Talking About Opening a file #include <stdio.h> FILE *fopen(const char *FILE, const char *MODE); Modes r - read w - write a - append b - binary + - combinations

  21. Or Closing a file #include <stdio.h> int fclose(FILE *FP);

  22. Character I/O #include <stdio.h> int putchar(int CH); int putc(int CH, FILE *FP); int getchar(void); int getc(FILE *FP);

  23. We talked about fgets char *fgets(char *s, int size, FILE *stream); • fgets() • reads in at most one less than size characters from stream • stores characters read into the buffer pointed to by s. • Stops reading after an EOF or a newline. • Stores a newline into the buffer if one is read • Stores a '\0' after the last character in the buffer. • Returns s on success and NULL on error or when end of file occurs while no characters have been read.

  24. Pop Quiz /* Here is the code */ char buf[8]; while(fgets(buf, sizeof(buf), stdin)) printf("Got [%s]\n", buf); Here is the input (each line is followed by a newline): 123456 abcdefgh 123456789012 What is the output?

  25. 123456 Got [123456 ] abcdefgh Got [abcdefg] Got [h ] 123456789012 Got [1234567] Got [89012 ] > fgets < input.txt Got [123456 ] Got [abcdefg] Got [h ] Got [1234567] Got [89012 ] > Solution

  26. Formatted I/O int printf(const char *format, ...); int fprintf(FILE *stream, const char *format, ...); int sprintf(char *str, const char *format, ...); void ham_VBAText(const char *format, ...); int scanf(const char *format, ...); int fscanf(FILE *stream, const char *format, ...); int sscanf(const char *str, const char *format, ...);

  27. What's up with the ... int printf(const char *format, ...);

  28. Variable Arguments printf("%d %d %d\n", a, b, c); Locals... FP Old FP Return Addr Return Val char *fmt a b c

  29. Variable Arguments another(a, b, c, 0); Locals... FP Old FP Return Addr Return Val a b c 0

  30. int main() { char buffer[1024]; strcpy (buffer, "The "); strcatv(buffer, "quick ", "brown ", "fox ", NULL); strcatv(buffer, "jumped ", "over ", NULL); strcatv(buffer, "the ", "lazy ", "dogs.", "\n", NULL); printf("%s", buffer); return EXIT_SUCCESS; }

  31. #include <stdio.h> #include <stdarg.h> #include <string.h> char *strcatv(char *dst, ...) { char *p; va_list arglist; va_start(arglist, dst); while ((p = va_arg(arglist, char *)) != NULL) strcat(dst, p); va_end(arglist); return dst; }

  32. #include <stdio.h> #include <stdarg.h> #include <string.h> char *strcatv(char *dst, ...) { char *p; va_list arglist; va_start(arglist, dst); while ((p = va_arg(arglist, char *)) != NULL) strcat(dst, p); va_end(arglist); return dst; }

  33. #include <stdio.h> #include <stdarg.h> #include <string.h> char *strcatv(char *dst, ...) { char *p; va_list arglist; va_start(arglist, dst); while ((p = va_arg(arglist, char *)) != NULL) strcat(dst, p); va_end(arglist); return dst; }

  34. #include <stdio.h> #include <stdarg.h> #include <string.h> char *strcatv(char *dst, ...) { char *p; va_list arglist; va_start(arglist, dst); while ((p = va_arg(arglist, char *)) != NULL) strcat(dst, p); va_end(arglist); return dst; }

  35. #include <stdio.h> #include <stdarg.h> #include <string.h> char *strcatv(char *dst, ...) { char *p; va_list arglist; va_start(arglist, dst); while ((p = va_arg(arglist, char *)) != NULL) strcat(dst, p); va_end(arglist); return dst; }

  36. #include <stdio.h> #include <stdarg.h> #include <string.h> char *strcatv(char *dst, ...) { char *p; va_list arglist; va_start(arglist, dst); while ((p = va_arg(arglist, char *)) != NULL) strcat(dst, p); va_end(arglist); return dst; }

More Related