FIT 5003-FIT5003 JAVA和C

August 19, 2021 FIT 5003 Software Security Assignment I (S2 2021) Total Marks 100 Due on Week 7 September 09, 2021, Friday, 11:59:00pm 1 Overview The learning objective of this assignment is for you to gain a first-hand experience on various vulnerabilities and attack in c programming language and get a deeper understanding on how to use cryptographic algo- rithms correctly in practice. All tasks in this assignment can be done on “SeedVM” as used in labs. Please refer to Section 2 for submission notes. 2 Submission You need to submit a lab report (one single PDF file) to describe what you have done and what you have observed with screen shots whenever necessary; you also need to provide explanation or codes to the observations that are interesting or surprising. In your report, you need to answer all the questions listed in this manual. Please answer each question using at most 100 words. Typeset your report into .pdf format (make sure it can be opened with Adobe Reader) and name it as the format: [Your Name]-[Student ID]- FIT5003-Assignment1, e.g., HarryPotter-12345678-FIT5003-Assignment1.pdf. All source code if required should be submitted according to the submission instruction provided on Moodle. In addition, if a demonstration video is required, you should record your screen demonstration with your voice explanation and upload the video to your Monash Google Drive. Your face should be visible at least at the beginning of the video interview. If you do not wish to have your face visible in the video, contact the teaching team at least a week before the deadline so as to arrange a physical interview. The shared URL of the video should be mentioned in your report wherever required. You can use this free tool to make the video:http://monash-panopto.aarnet.edu.au/ ; other tools are also fine. Then, please upload the PDF file to Moodle. Note: the assignment is due on September 09, 2021, Friday, 11:59:00 pm Late submission penalty: 10 points deduction per day. If you require a special consideration, the application should be submitted and notified at least three days in advance. Special Considerations are handled by and approved by the faculty and not by the teaching team (unless the special consideration is for a small time period extension of one or two days). Zero tolerance on plagiarism: If you are found cheating, penalties will be applied, i.e., a zero grade for the unit. University polices can be found at https: //www.monash.edu/students/academic/policies/academic-integrity 1 3 C Code Vulnerabilities [80 Marks] The learning objective of this part is for you to gain the first-hand experience on buffer-overflow vulnerability by putting what you have learned about the vulnerability from class into action. Buffer overflow is defined as the condition in which a program attempts to write data beyond the boundaries of pre-allocated fixed length buffers. This vulnerability can be utilized by an attacker to alter the flow control of the program, even execute arbitrary pieces of code to enable remote access attacks. This vulnerability arises due to the mixing of the storage for data (e.g. buffers) and the storage for controls (e.g. return addresses): an overflow in the data part can affect the control flow of the program, because an overflow can change the return address. In this part, you will be given a program with a buffer-overflow vulnerability; the task is to develop a scheme to exploit the vulnerability and finally send a remote access to an attacker. 3.1 Initial setup You can execute the tasks using our pre-built Ubuntu virtual machines. Ubuntu and other Linux dis- tributions have implemented several security mechanisms to make the buffer-overflow attack difficult. To simplify our attacks, we need to disable them first. Address Space Randomization. Ubuntu and several other Linux-based systems uses address space ran- domization to randomize the starting address of heap and stack. This makes guessing the exact addresses difficult; guessing addresses is one of the critical steps of buffer-overflow attacks. In this part, we disable these features using the following commands: $ su root Password: (enter root password “seedubuntu”) # sysctl -w kernel.randomize_va_space=0 # exit The StackGuard Protection Scheme. The GCC compiler implements a security mechanism called “Stack Guard” to prevent buffer overflows. In the presence of this protection, buffer overflow will not work. You can disable this protection if you compile the program using the -fno-stack-protector switch. For example, to compile a program example.c with Stack Guard disabled, you may use the following command: $ gcc -fno-stack-protector example.c Non-Executable Stack. Ubuntu used to allow executable stacks, but this has now changed: the binary images of programs (and shared libraries) must declare whether they require executable stacks or not, i.e., they need to mark a field in the program header. Kernel or dynamic linker uses this marking to decide whether to make the stack of this running program executable or non-executable. This marking is done automatically by the recent versions of gcc, and by default, the stack is set to be non-executable. To change that, use the following option when compiling programs: For executable stack: $ gcc -z execstack -o test test.c For non-executable stack: $ gcc -z noexecstack -o test test.c 2 3.2 Task 1: Shellcode Practice Before you start the attack, we want you to exercise with a shellcode example. A shellcode is the code to launch a shell. It is a list of carefully crafted instructions created by malicious users/attackers so that it can be executed once the code is injected into a vulnerable program. Therefore, it has to be loaded into the memory so that we can force the vulnerable program to jump to it. Consider the following program: #include int main( ) { char *name[2]; name[0] = ‘‘/bin/sh’’; name[1] = NULL; execve(name[0], name, NULL); } The shellcode that we use is the assembly version of the above program. The following program shows you how to launch a shell by executing a shellcode stored in a buffer. Please compile and run the following code, and see whether a shell is invoked. Please briefly describe your observations. [Marking scheme: 2 marks for the screenshot and 3 marks for the explanation] Question 1 /* call_shellcode.c */ /*A program that creates a file containing code for launching shell*/ #include #include #include const char code[] = “x31xc0” /* Line 1: xorl %eax,%eax */ “x50” /* Line 2: pushl %eax */ “x68″”//sh” /* Line 3: pushl $0x68732f2f */ “x68″”/bin” /* Line 4: pushl $0x6e69622f */ “x89xe3” /* Line 5: movl %esp,%ebx */ “x50” /* Line 6: pushl %eax */ “x53” /* Line 7: pushl %ebx */ “x89xe1” /* Line 8: movl %esp,%ecx */ “x99” /* Line 9: cdq */ “xb0x0b” /* Line 10: movb $0x0b,%al */ “xcdx80” /* Line 11: int $0x80 */ ; int main(int argc, char **argv) 3 { char buf[sizeof(code)]; strcpy(buf, code); ((void(*)( ))buf)( ); } Please use the following command to compile the code (don’t forget the execstack option): $ gcc -z execstack -g -o call_shellcode call_shellcode.c 3.3 The Vulnerable Program In this Section we introduce the vulnerable program (called stack.c). You can find the source code in the Unit’s Moodle. The program acts as an authentication server that provides an authorized user a unique security token. For authentication a user-client provides as a payloads in the buf variable a username and a password and the vulnerable program checks if these credentials are stored in a password file. If the user has provided the correct password then a unique security token is send to this user. The password file is called fit5003passwords) and is stored in the same folder as the server program. For the assignment, we assume that the communication is secured by some other means so that the username and password cannot be eavesdropped and that the attacker cannot directly access the password file. The program has several vulnerabilities. For this assignment, we focus on the vulnerabilities in the check_auth function that is shown below. int check_auth(int sock,Line users[], char* auth_decoded) { // auth_decoded is of the form “:”, separate them char *auth_username; char *auth_pass_p=NULL; char auth_password[36]; auth_pass_p=auth_password; auth_username = strtok(auth_decoded, “:”); strcpy(auth_pass_p,strtok(NULL, “n”)); printf(“test testn”); // find auth_username in users (each line is char* password_md5 = NULL; int ul = strlen(auth_username); for (int i = 0; strcmp(users[i], “”) != 0; i++) { if (strncmp(users[i], auth_username, ul) == 0 && users[i][ul] == ’:’) { password_md5 = users[i] + ul + 1; // part, after the ’:’ break; } } close(STDOUT_FILENO); close(STDERR_FILENO); dup2(sock, STDOUT_FILENO); dup2(sock, STDERR_FILENO); 4 // check if user is found if (password_md5 == NULL) { printf(“User Unauthorizedrn”); printf(“Invalid user: “); printf(auth_username); printf(“”rnrn””); return 0; } // check password’s md5 char auth_password_md5[33]; md5_hex(auth_password