看不见的彼方:互换空间——小菜一碟

打印 上一主题 下一主题

主题 1037|帖子 1037|积分 3111

马上注册,结交更多好友,享用更多功能,让你轻松玩转社区。

您需要 登录 才可以下载或查看,没有账号?立即注册

x



有个蓝色的链接,先去看看两年前的题目标write up
(https://github.com/USTC-Hackergame/hackergame2022-writeups/blob/master/official/%E7%9C%8B%E4%B8%8D%E8%A7%81%E7%9A%84%E5%BD%BC%E6%96%B9/README.md)
从别人的write up中相识到,可以用信号和IPC来传递数据,而这个IPC指的就是消息队列(msgget 等)和共享内存(shmget 等),留意一定要使用System V的 API,因为posix的那几个会依赖文件系统而不能使用。
历程间通信的题目解决了,接下来就是内存限制的处置处罚了。固然不能完全复制,但是一次复制个2MiB 照旧没题目标。开一个2MiB大小的共享内存空间,然后前半部分用来把A的文件内容传给B,后半部分用来把 B 的文件内容传给 A,写入到文件的时候直接原位置覆盖写入即可。每次传递两个1MiB 大小的文件片断,再加上用消息队列跨历程同步,整个事情就成了。
容器内存限制 316 MiB,你提交的程序文件会复制为两份,分别占用一份内存空间。环境限制总 PID 数为 32。对于 chroot 内部的历程,只有 /space 可读写。/space(/home/pwn/A/space/ 和 /home/pwn/B/space/)为 tmpfs,使用内存空间。

已经尝试过让AI天生代码,但照旧不行,代码这块我不认识,下面是大佬的write up的代码:
  1. #include <unistd.h>
  2. #include <signal.h>
  3. #include <stdio.h>
  4. #include <stdlib.h>
  5. #include <fcntl.h>
  6. #include <sys/stat.h>
  7. #include <sys/msg.h>
  8. #include <sys/shm.h>
  9. void perror_exit(char* message){
  10.         perror(message);
  11.         exit(-1);
  12. }
  13. struct message {
  14.     long type;
  15.     char buffer[4];
  16. };
  17. int main()
  18. {
  19.         printf("a start\n");
  20.         int mqab=msgget(12450,0666 |IPC_CREAT);
  21.         if(mqab<0){
  22.                 perror_exit("msgget swapab error");
  23.         }
  24.         int mqba=msgget(12451,0666 |IPC_CREAT);
  25.         if(mqba<0){
  26.                 perror_exit("msgget swapba error");
  27.         }
  28.         int shm=shmget(12452,2*1024*1024,0666 |IPC_CREAT);
  29.         if(mqba<0){
  30.                 perror_exit("shmget error");
  31.         }
  32.         void* mem=shmat(shm,0,0);
  33.         if(mem==(void*)(-1)){
  34.                 perror_exit("shmat error");
  35.         }
  36.         int fd=open("/space/file",O_RDWR);
  37.         if(fd<0){
  38.                 perror_exit("open error");
  39.         }
  40.         printf("a ok\n");
  41.         char* read_start=((char*)(mem));
  42.         char* write_start=((char*)(mem))+1024*1024;
  43.         for(int i=0;i<128;i++){
  44.                 int segment_start=i*1024*1024;
  45.                 // 读出文件内容
  46.                 off_t read_off=lseek(fd,segment_start,SEEK_SET);
  47.                 if(read_off<0){
  48.                         perror_exit("lseek error");
  49.                 }
  50.                 int read_count=0;
  51.                 while(read_count<1024*1024){
  52.                         int read_len=read(fd,read_start+read_count,1024*1024-read_count);
  53.                         if(read_len<0){
  54.                                 perror_exit("read error");
  55.                         }
  56.                         read_count+=read_len;
  57.                 }
  58.                 // 发送同步信号
  59.                 struct message out;
  60.                 out.type=1;
  61.                 if (msgsnd(mqab, &out, sizeof (struct message), 0) <0) {
  62.                         perror_exit("msgsnd error");
  63.         }
  64.                 // 接收同步信号
  65.                 struct message in;
  66.                 if (msgrcv(mqba, &in, sizeof (struct message),0, 0) <0) {
  67.                         perror_exit("msgrcv error");
  68.         }
  69.                 // 写回文件内容
  70.                 off_t write_off=lseek(fd,segment_start,SEEK_SET);
  71.                 if(write_off<0){
  72.                         perror_exit("lseek error");
  73.                 }
  74.                 int write_count=0;
  75.                 while(write_count<1024*1024){
  76.                         int write_len=write(fd,write_start+write_count,1024*1024-write_count);
  77.                         if(write_len<0){
  78.                                 perror_exit("write error");
  79.                         }
  80.                         write_count+=write_len;
  81.                 }
  82.         }
  83.         printf("a complete\n");
  84. }
复制代码
  1. #include <unistd.h>
  2. #include <signal.h>
  3. #include <stdio.h>
  4. #include <stdlib.h>
  5. #include <fcntl.h>
  6. #include <sys/stat.h>
  7. #include <sys/msg.h>
  8. #include <sys/shm.h>
  9. void perror_exit(char* message){
  10.         perror(message);
  11.         exit(-1);
  12. }
  13. struct message {
  14.     long type;
  15.     char buffer[4];
  16. };
  17. int main()
  18. {
  19.         printf("b start\n");
  20.         int mqab=msgget(12450,0666 |IPC_CREAT);
  21.         if(mqab<0){
  22.                 perror_exit("msgget swapab error");
  23.         }
  24.         int mqba=msgget(12451,0666 |IPC_CREAT);
  25.         if(mqba<0){
  26.                 perror_exit("msgget swapba error");
  27.         }
  28.         int shm=shmget(12452,2*1024*1024,0666 |IPC_CREAT);
  29.         if(mqba<0){
  30.                 perror_exit("shmget error");
  31.         }
  32.         void* mem=shmat(shm,0,0);
  33.         if(mem==(void*)(-1)){
  34.                 perror_exit("shmat error");
  35.         }
  36.         int fd=open("/space/file",O_RDWR);
  37.         if(fd<0){
  38.                 perror_exit("open error");
  39.         }
  40.         printf("b ok\n");
  41.         char* read_start=((char*)(mem))+1024*1024;
  42.         char* write_start=((char*)(mem));
  43.         for(int i=0;i<128;i++){
  44.                 int segment_start=i*1024*1024;
  45.                 // 接收同步信号
  46.                 struct message in;
  47.                 if (msgrcv(mqab, &in, sizeof (struct message),0, 0) <0) {
  48.                         perror_exit("msgrcv error");
  49.         }
  50.                 // 读出文件内容
  51.                 off_t read_off=lseek(fd,segment_start,SEEK_SET);
  52.                 if(read_off<0){
  53.                         perror_exit("lseek error");
  54.                 }
  55.                 int read_count=0;
  56.                 while(read_count<1024*1024){
  57.                         int read_len=read(fd,read_start+read_count,1024*1024-read_count);
  58.                         if(read_len<0){
  59.                                 perror_exit("read error");
  60.                         }
  61.                         read_count+=read_len;
  62.                 }
  63.                 // 写回文件内容
  64.                 off_t write_off=lseek(fd,segment_start,SEEK_SET);
  65.                 if(write_off<0){
  66.                         perror_exit("lseek error");
  67.                 }
  68.                 int write_count=0;
  69.                 while(write_count<1024*1024){
  70.                         int write_len=write(fd,write_start+write_count,1024*1024-write_count);
  71.                         if(write_len<0){
  72.                                 perror_exit("write error");
  73.                         }
  74.                         write_count+=write_len;
  75.                 }
  76.                 // 发送同步信号
  77.                 struct message out;
  78.                 out.type=1;
  79.                 if (msgsnd(mqba, &out, sizeof (struct message), 0) <0) {
  80.                         perror_exit("msgsnd error");
  81.         }
  82.         }
  83.         printf("b complete\n");
  84. }
复制代码
编译之后上传文件:






乐成得到flag:flag{just A p1ece 0f cake_2e65492b77}

免责声明:如果侵犯了您的权益,请联系站长,我们会及时删除侵权内容,谢谢合作!更多信息从访问主页:qidao123.com:ToB企服之家,中国第一个企服评测及商务社交产业平台。
回复

使用道具 举报

0 个回复

倒序浏览

快速回复

您需要登录后才可以回帖 登录 or 立即注册

本版积分规则

河曲智叟

论坛元老
这个人很懒什么都没写!
快速回复 返回顶部 返回列表