以下程序可以逐行输出由language数组元素所指向的5个字符串。 #include<stdio.h> int main(void) { const char *language[] = {"BASIC", "FORTRAN", "PROLOG", "JAVA", "C++" } ; const char ; int k; for(k = 0 ; k < 5 ; k++) { ; printf ("%s\n", *q); } return 0; }
时间: 2023-12-14 20:37:10 浏览: 908
以下是可以逐行输出由language数组元素所指向的5个字符串的程序:
```
#include <stdio.h>
int main(void) {
const char *language[] = {"BASIC", "FORTRAN", "PROLOG", "JAVA", "C++"};
const char *q;
int k;
for (k = 0; k < 5; k++) {
q = language[k];
printf("%s\n", q);
}
return 0;
}
```
程序中,`const char *q;` 声明了一个指向常量字符串的指针变量 q。在 for 循环中,`q = language[k];` 将 q 指向 language 数组中第 k 个元素所指向的字符串。然后,`printf ("%s\n", *q);` 可以输出 q 指向的字符串。最终,程序可以逐行输出由 language 数组元素所指向的 5 个字符串。
相关问题
#include<stdio.h> char *strc(char *s1,char *s2) { char *p=s1; while (*s2!='\0') { *p++=*s2++; } return s1; } int main(void) { char s1[30]="computer OK!",s2[]="language",*pt; pt=strc(s1,s2); printf("%s\n",pt); }
这段代码的作用是在字符串s1的末尾添加字符串s2,并返回s1的地址。具体实现是通过指针p指向s1的首地址,然后遍历字符串s2,依次将其字符赋值给p所指向的地址,同时p不断向后移动,直到遍历完s2。最后返回s1的地址。
在这个具体的例子中,s1的初始值为"computer OK!",s2的值为"language",执行strc函数后,s1的值变为"computer OK!language",并且返回s1的地址。最终输出的就是s1的值"computer OK!language"。
第一题:对于下面的C语言程序,通过调试,给出适当的输入,使得bar函数能够得到执行。要求给出调试过程的界面。 #include <stdio.h> #include <string.h> void foo(const char* input) { char buf[10]; printf(“My stack looks like:\n%p\n%p\n%p\n%p\n%p\n%p\n\n”); strcpy(buf,input); printf(“%s\n”,buf); printf(“Now the stack looks like :\n%p\n%p\n%p\n%p\n%p\n%p\n\n”); } void bar(void) { printf(“Augh! I’ve been hacked!\n”); } int main(int argc, char* argv[]) { printf(“Address of foo=%p\n”,foo); printf(“Address of bar=%p\n”,bar); if(argc!=2) { printf(“Please supply a string as an argument!\n”); return -1; } foo(argv[1]); return 0; }
这是一道经典的栈溢出漏洞题目。我们需要输入一段长度超过 10 个字符的字符串,覆盖掉 buf 数组后面的地址,从而控制程序的执行流程,使其执行 bar 函数。
调试过程如下:
1. 编译程序并生成可执行文件,使用 gdb 命令进行调试。
```
$ gcc -g -o vuln vuln.c
$ gdb vuln
```
2. 在 gdb 中设置断点,以便在执行到 bar 函数时停下来。
```
(gdb) break bar
Breakpoint 1 at 0x400661: file vuln.c, line 15.
```
3. 运行程序并输入一个长度超过 10 个字符的字符串,如 "AAAAAAAAAA"。
```
(gdb) run AAAAAAAAAA
Starting program: /home/user/vuln AAAAAAAAAA
Address of foo=0x4006c6
Address of bar=0x400661
My stack looks like:
0x7fffffffdf30
0x7fffffffdf28
0x7fffffffdf20
0x7fffffffdf18
0x7fffffffdf10
0x7fffffffdf08
AAAAAAAAAA
Now the stack looks like :
0x7fffffffdf30
0x7fffffffdf28
0x7fffffffdf20
0x7fffffffdf18
0x7fffffffdf10
0x7fffffffdf08
[Inferior 1 (process 10174) exited with code 01]
```
4. 程序输出 "Augh! I’ve been hacked!",表明我们已经成功地控制了程序的执行流,并使其跳转到了 bar 函数。
```
Breakpoint 1, bar () at vuln.c:15
15 printf("Augh! I’ve been hacked!\n");
(gdb) info frame
Stack level 0, frame at 0x7fffffffde90:
rip = 0x400661 in bar (vuln.c:15); saved rip 0x4007c1
callee = 0x4006c6 <foo>
source language c.
Arglist at 0x7fffffffde80, args:
Locals at 0x7fffffffde80, Previous frame's sp is 0x7fffffffde90
Saved registers:
rbp at 0x7fffffffde80, rip at 0x7fffffffde88
(gdb) quit
```
至此,我们成功地利用了栈溢出漏洞,控制了程序的执行流程,使其执行了 bar 函数。
阅读全文