IDA使用-2023CICSN华中赛区pwn题逆向为例


2023华中pwn题逆向参考视频教程

相关字节标识

_WORD(1个字=2个字节=16位)
_DWORD(2个字=4个字节=32位)
_QWORD(4个字=8个字节=64位)
_OWORD(8个字=16个字节=128位

DB (Define Byte): 用于定义单字节(8位)的数据。
DW (Define Word): 用于定义字(Word)大小的数据,通常为2字节(16位)。
DD (Define Doubleword): 用于定义双字(Doubleword)大小的数据,通常为4字节(32位)。
DQ (Define Quadword): 用于定义四字(Quadword)大小的数据,通常为8字节(64位)。

导入函数和导出函数

在C语言中,导入函数和导出函数是实现模块化编程的关键技术,它们分别用于在不同模块之间共享和使用函数。以下是具体分析:

  • 导出函数:在C语言中,当一个函数被声明为导出时,它意味着这个函数可以在其他模块中被调用。这通常通过特定的编译器指令或关键字来实现,例如在Windows平台的C/C++中使用__declspec(dllexport)来导出DLL中的函数。

在这里插入图片描述

  • 导入函数:与导出函数相对应,导入函数是指在当前模块中引用外部模块定义的函数。在C语言中,导入函数通常涉及到包含相应的头文件,并且确保链接时包含了定义这些函数的目标文件或库文件。

在这里插入图片描述

找程序入口函数

export找到start,start中找到main
在这里插入图片描述

选项设置

在这里插入图片描述

重命名

在这里插入图片描述

CISCN2023华中赛区分区赛AWD

IDA源码

main

__int64 __fastcall main(int a1, char **a2, char **a3)
{
  int v4; // [rsp+Ch] [rbp-14h]
  void *ptr; // [rsp+10h] [rbp-10h]
  void *v6; // [rsp+18h] [rbp-8h]

  setvbuf(stdin, 0LL, 2, 0LL);
  setvbuf(stdout, 0LL, 2, 0LL);
  setvbuf(stderr, 0LL, 2, 0LL);
  alarm(0x20u);
  qword_50E0 = sub_141B();
  *(_DWORD *)qword_50E0 = 0;
  qword_5150 = qword_50E0;
  *(_BYTE *)(qword_50E0 + 4) = 47;
  strncpy(dest, (const char *)(qword_50E0 + 4), 1uLL);
  do
  {
    printf("\x1B[36mmybash:%s$ \x1B[0m", dest);
    ptr = (void *)sub_25D5();
    v6 = (void *)sub_247F(ptr);
    v4 = sub_23CA(v6);
    free(ptr);
    free(v6);
  }
  while ( v4 );
  return 0LL;
}

构造结构体

sub_141B()

该函数对建立的堆的不同位置进行变量设置,为了更方便的查看设置的位置,可以设置一个结构体来替代

_QWORD *sub_141B()
{
  _QWORD *v1; // [rsp+8h] [rbp-8h]

  v1 = malloc(0x40uLL);
  if ( !v1 )
    _exit(0);
  memset((char *)v1 + 4, 0, 0x10uLL);
  v1[7] = 0LL;
  v1[5] = 0LL;
  v1[4] = 0LL;
  v1[6] = 0LL;
  return v1;
}

打开局部变量类型的视图

在这里插入图片描述
在这里插入图片描述

增加变量类型

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

重新定义变量类型

在这里插入图片描述
在这里插入图片描述
然后代码变为

SomeStruct *sub_141B()
{
  SomeStruct *v1; // [rsp+8h] [rbp-8h]

  v1 = (SomeStruct *)malloc(0x40uLL);
  if ( !v1 )
    _exit(0);
  memset(&v1->gap[4], 0, 0x10uLL);
  *(_QWORD *)&v1->gap[56] = 0LL;
  *(_QWORD *)&v1->gap[40] = 0LL;
  *(_QWORD *)&v1->gap[32] = 0LL;
  *(_QWORD *)&v1->gap[48] = 0LL;
  return v1;
}
发现在距离起始四个字节后的十六个字节都设置为0
  memset(&v1->gap[4], 0, 0x10uLL);

memset函数

memset函数是C语言标准库中的一个用于内存操作的函数,它主要用于将某一块内存空间的内容设置为指定的值。

memset函数的原型为:

void *memset(void *s, int c, size_t n);
  • void *s:指向要填充的内存块的指针。
  • int c:需要设置的值,该值会被转换为无符号字符后用来设置内存块。
  • size_t n:要设置的内存块的字节数。

再次设置变量类型并重新定义

在这里插入图片描述
在这里插入图片描述
结果代码

SomeStruct *sub_141B()
{
  SomeStruct *v1; // [rsp+8h] [rbp-8h]

  v1 = (SomeStruct *)malloc(0x40uLL);
  if ( !v1 )
    _exit(0);
  memset(v1->some_array, 0, sizeof(v1->some_array));
  *(_QWORD *)&v1->gap[36] = 0LL;
  *(_QWORD *)&v1->gap[20] = 0LL;
  *(_QWORD *)&v1->gap[12] = 0LL;
  *(_QWORD *)&v1->gap[28] = 0LL;
  return v1;
}

再次设置变量类型并重新定义

在这里插入图片描述

SomeStruct *sub_141B()
{
  SomeStruct *v1; // [rsp+8h] [rbp-8h]

  v1 = (SomeStruct *)malloc(0x40uLL);
  if ( !v1 )
    _exit(0);
  memset(v1->some_array, 0, sizeof(v1->some_array));
  *(_QWORD *)&v1->gap[24] = 0LL;
  *(_QWORD *)&v1->gap[8] = 0LL;
  *(_QWORD *)v1->gap = 0LL;
  *(_QWORD *)&v1->gap[16] = 0LL;
  return v1;
}

再次设置变量类型并重新定义

在这里插入图片描述

SomeStruct *sub_141B()
{
  SomeStruct *v1; // [rsp+8h] [rbp-8h]

  v1 = (SomeStruct *)malloc(0x40uLL);
  if ( !v1 )
    _exit(0);
  memset(v1->some_array, 0, sizeof(v1->some_array));
  v1->ptr56 = 0LL;
  v1->ptr40 = 0LL;
  v1->ptr32 = 0LL;
  v1->ptr48 = 0LL;
  return v1;
}

设置函数名

在这里插入图片描述

标记已经分析完

在这里插入图片描述

找到引用函数的各个地方

在这里插入图片描述
在这里插入图片描述

对变量重新定义变量类型

在这里插入图片描述

__int64 __fastcall main(int a1, char **a2, char **a3)
{
  int v4; // [rsp+Ch] [rbp-14h]
  void *ptr; // [rsp+10h] [rbp-10h]
  void *v6; // [rsp+18h] [rbp-8h]

  setvbuf(stdin, 0LL, 2, 0LL);
  setvbuf(stdout, 0LL, 2, 0LL);
  setvbuf(stderr, 0LL, 2, 0LL);
  alarm(0x20u);
  qword_50E0 = SomeStruct::CreateInstance();
  qword_50E0->unkown_0 = 0;
  qword_5150 = qword_50E0;
  qword_50E0->some_array[0] = 47;
  strncpy(dest, qword_50E0->some_array, 1uLL);
  do
  {
    printf("\x1B[36mmybash:%s$ \x1B[0m", dest);
    ptr = (void *)sub_25D5();
    v6 = (void *)sub_247F(ptr);
    v4 = sub_23CA(v6);
    free(ptr);
    free(v6);
  }
  while ( v4 );
  return 0LL;
}

转换为字符

在这里插入图片描述

格式化字符串"\x1B[36mmybash:%s$ \x1B[0m"

字符串 “\x1B[36mmybash:%s$ \x1B[0m” 是一个包含ANSI转义序列的字符串,用于在终端上显示颜色文本。在这个字符串中:

\x1B[36m 是一个ANSI转义序列,用于将随后的文本颜色设置为青色(Cyan)。\x1B 是ESC字符的十六进制表示,[ 表示转义序列的开始,36 是选择青色的颜色代码,而 m 表示结束这个颜色设置。
mybash:%s$ 是实际要显示的文本,其中 %s 可能是一个占位符,用于格式化字符串时替换为某个特定的值。
\x1B[0m 是另一个ANSI转义序列,用于重置文本颜色到默认设置。这里 0 表示默认颜色,而 m 同样表示结束这个设置。

sub_25D5()

_BYTE *sub_25D5()
{
  int v1; // [rsp+Ch] [rbp-14h]
  int v2; // [rsp+10h] [rbp-10h]
  int v3; // [rsp+14h] [rbp-Ch]
  _BYTE *ptr; // [rsp+18h] [rbp-8h]

  v1 = 528;
  v2 = 0;
  ptr = malloc(0x210uLL);
  if ( !ptr )
    _exit(0);
  while ( 1 )
  {
    v3 = getchar();
    if ( v3 == -1 || v3 == 10 )
      break;
    ptr[v2++] = v3;
    if ( v2 >= v1 && v1 <= 2147483639 )
    {
      v1 += 496;
      ptr = realloc(ptr, v1);
      if ( !ptr )
      {
        fwrite("mybash: allocation error\n", 1uLL, 0x19uLL, stderr);
        exit(1);
      }
    }
  }
  ptr[v2] = 0;
  return ptr;
}

-1转换与相关变量与函数命名

在这里插入图片描述

设置sub_25D5()

这里根据每次输入一个字符将分配得到的堆指针设置为字符指针类型

void __fastcall read_line()
{
  int high; // [rsp+Ch] [rbp-14h]
  int i; // [rsp+10h] [rbp-10h]
  int tmp_char; // [rsp+14h] [rbp-Ch]
  char *input_content_line; // [rsp+18h] [rbp-8h]

  high = 528;
  i = 0;
  input_content_line = (char *)malloc(0x210uLL);
  if ( !input_content_line )
    _exit(0);
  while ( 1 )
  {
    tmp_char = getchar();
    if ( tmp_char == (unsigned int)EOF || tmp_char == '\n' )
      break;
    input_content_line[i++] = tmp_char;
    if ( i >= high && high <= 2147483639 )
    {
      high += 496;
      input_content_line = (char *)realloc(input_content_line, high);
      if ( !input_content_line )
      {
        fwrite("mybash: allocation error\n", 1uLL, 0x19uLL, stderr);
        exit(1);
      }
    }
  }
  input_content_line[i] = 0;
}

sub_247F(char *a1)

_QWORD *__fastcall sub_247F(char *a1)
{
  int v2; // [rsp+10h] [rbp-20h]
  int v3; // [rsp+14h] [rbp-1Ch]
  _QWORD *ptr; // [rsp+18h] [rbp-18h]
  char *i; // [rsp+20h] [rbp-10h]
  _QWORD *v6; // [rsp+28h] [rbp-8h]

  v2 = 64;
  v3 = 0;
  v6 = malloc(0x200uLL);
  if ( !v6 )
    _exit(0);
  ptr = v6;
  for ( i = strtok(a1, " \t\r\n\a"); i; i = strtok(0LL, " \t\r\n\a") )
  {
    ptr[v3++] = i;
    if ( v3 >= v2 )
    {
      v2 += 64;
      ptr = realloc(ptr, 8LL * v2);
      if ( !ptr )
      {
        fwrite("mybash: allocation error\n", 1uLL, 0x19uLL, stderr);
        exit(1);
      }
    }
  }
  ptr[v3] = 0LL;
  return ptr;
}

设置sub_247F(char *a1)函数

这里i是地址,所以ptr应该是双指针
在这里插入图片描述

char **__fastcall split_string(char *content_line)
{
  int high; // [rsp+10h] [rbp-20h]
  int cur_pos; // [rsp+14h] [rbp-1Ch]
  char **split_content_ptr; // [rsp+18h] [rbp-18h]
  char *one_split_content_ptr; // [rsp+20h] [rbp-10h]
  char **temp_chunk_ptr; // [rsp+28h] [rbp-8h]

  high = 64;
  cur_pos = 0;
  temp_chunk_ptr = (char **)malloc(0x200uLL);
  if ( !temp_chunk_ptr )
    _exit(0);
  split_content_ptr = temp_chunk_ptr;
  for ( one_split_content_ptr = strtok(content_line, " \t\r\n\a");
        one_split_content_ptr;
        one_split_content_ptr = strtok(0LL, " \t\r\n\a") )
  {
    split_content_ptr[cur_pos++] = one_split_content_ptr;
    if ( cur_pos >= high )
    {
      high += 64;
      split_content_ptr = (char **)realloc(split_content_ptr, 8LL * high);
      if ( !split_content_ptr )
      {
        fwrite("mybash: allocation error\n", 1uLL, 0x19uLL, stderr);
        exit(1);
      }
    }
  }
  split_content_ptr[cur_pos] = 0LL;
  return split_content_ptr;
}

sub_23CA(const char **a1)

__int64 __fastcall sub_23CA(const char **a1)
{
  int i; // [rsp+1Ch] [rbp-4h]

  if ( !*a1 )
    return 1LL;
  for ( i = 0; i < (int)sub_1523(); ++i )
  {
    if ( !strcmp(*a1, (const char *)*(&off_5020 + i)) )
      return ((__int64 (__fastcall *)(const char **))funcs_2446[i])(a1);
  }
  printf("%s: ERROR\n", *a1);
  return 0LL;
}

设置sub_23CA(const char **a1)函数

在这里插入图片描述

__int64 __fastcall instruction_proccess(const char **split_content_ptr_array)
{
  int i; // [rsp+1Ch] [rbp-4h]

  if ( !*split_content_ptr_array )
    return 1LL;
  for ( i = 0; i < (int)return_7(); ++i )
  {
    if ( !strcmp(*split_content_ptr_array, struction_name_ptr_array[i]) )
      return struction_function_ptr_array[i](split_content_ptr_array);
  }
  printf("%s: ERROR\n", *split_content_ptr_array);
  return 0LL;
}

sub_1523()

__int64 sub_1523()
{
  return 7LL;
}

设置sub_1523()函数

__int64 return_7()
{
  return 7LL;
}

h更换数据形式

在这里插入图片描述
对应的各个字符串
在这里插入图片描述

更改各个函数名

在这里插入图片描述

__int64 __fastcall command_touch(__int64 a1)

__int64 __fastcall command_touch(__int64 a1)
{
  int v2; // [rsp+1Ch] [rbp-14h]
  void *ptr56; // [rsp+20h] [rbp-10h]
  SomeStruct *Instance; // [rsp+28h] [rbp-8h]

  v2 = 1;
  if ( !*(_QWORD *)(a1 + 8) )
    fwrite("mybash: missing operand\n", 1uLL, 0x18uLL, stderr);
  while ( *(_QWORD *)(8LL * v2 + a1) )
  {
    ptr56 = qword_5150->ptr56;
    if ( (unsigned __int8)sub_13C9((__int64)ptr56, *(const char **)(8LL * v2 + a1)) != 1 )
    {
      ++v2;
    }
    else
    {
      Instance = SomeStruct::CreateInstance();
      Instance->unkown_0 = 1;
      sub_166E(Instance, *(_QWORD *)(8LL * v2 + a1));
      if ( qword_5150->ptr56 )
        sub_1628(ptr56, Instance);
      else
        qword_5150->ptr56 = Instance;
      ++v2;
    }
  }
  return 1LL;
}

修改后的__int64 __fastcall command_touch(__int64 a1)

__int64 __fastcall command_touch(char **args)
{
  int parameter_position; // [rsp+1Ch] [rbp-14h]
  SomeStruct *main_save_instance_ptr_of_first_file_ptr; // [rsp+20h] [rbp-10h]
  SomeStruct *Instance_ptr; // [rsp+28h] [rbp-8h]

  parameter_position = 1;
  if ( !args[1] )
    fwrite("mybash: missing operand\n", 1uLL, 0x18uLL, stderr);
  while ( args[parameter_position] )
  {
    main_save_instance_ptr_of_first_file_ptr = main_save_instance_ptr->first_son;
    if ( (unsigned __int8)SomeStruct::Folder_Not_Eixst(
                            main_save_instance_ptr_of_first_file_ptr,
                            args[parameter_position]) != 1 )
    {
      ++parameter_position;
    }
    else
    {
      Instance_ptr = SomeStruct::CreateInstance();
      Instance_ptr->isfile = 1;
      SomeStruct::set_some_array(Instance_ptr, args[parameter_position]);
      if ( main_save_instance_ptr->first_son )
        sub_1628(main_save_instance_ptr_of_first_file_ptr, Instance_ptr);
      else
        main_save_instance_ptr->first_son = Instance_ptr;
      ++parameter_position;
    }
  }
  return 1LL;
}

__int64 __fastcall command_mkdir(__int64 a1)

__int64 __fastcall command_mkdir(__int64 a1)
{
  char v1; // al
  int v3; // [rsp+1Ch] [rbp-14h]
  void *ptr56; // [rsp+20h] [rbp-10h]
  SomeStruct *Instance; // [rsp+28h] [rbp-8h]

  v3 = 1;
  if ( !*(_QWORD *)(a1 + 8) )
    fwrite("mybash: missing operand\n", 1uLL, 0x18uLL, stderr);
  while ( *(_QWORD *)(8LL * v3 + a1) )
  {
    ptr56 = qword_5150->ptr56;
    ((void (__fastcall *)())((char *)&sub_13C8 + 1))();
    if ( v1 != 1 )
    {
      fprintf(stderr, aMybashCannotCr, *(_QWORD *)(8LL * v3++ + a1));
    }
    else
    {
      Instance = SomeStruct::CreateInstance();
      Instance->unkown_0 = 0;
      Instance->ptr48 = qword_5150;
      sub_166E(Instance, *(_QWORD *)(8LL * v3 + a1));
      if ( qword_5150->ptr56 )
        sub_1628(ptr56, Instance);
      else
        qword_5150->ptr56 = Instance;
      ++v3;
    }
  }
  return 1LL;
}
void sub_13C8()
{
  JUMPOUT(0x13CALL);
}

修改后的__int64 __fastcall command_mkdir(const char **args)

__int64 __fastcall command_mkdir(const char **args)
{
  // [COLLAPSED LOCAL DECLARATIONS. PRESS KEYPAD CTRL-"+" TO EXPAND]

  parameter_position = 1;
  if ( !args[1] )
    fwrite("mybash: missing operand\n", 1uLL, 0x18uLL, stderr);
  while ( args[parameter_position] )
  {
    main_save_instance_ptr_of_first = main_save_instance_ptr->first_son;
    if ( (unsigned __int8)SomeStruct::Folder_Not_Eixst(main_save_instance_ptr_of_first, args[parameter_position]) != 1 )
    {
      fprintf(stderr, aMybashCannotCr, args[parameter_position++]);
    }
    else
    {
      mkdir_create_Instance_ptr = SomeStruct::CreateInstance();
      mkdir_create_Instance_ptr->isfile = 0;    // 0为目录
      mkdir_create_Instance_ptr->parent = main_save_instance_ptr;
      SomeStruct::set_some_array(mkdir_create_Instance_ptr, args[parameter_position]);
      if ( main_save_instance_ptr->first_son )
        sub_1628(main_save_instance_ptr_of_first, mkdir_create_Instance_ptr);
      else
        main_save_instance_ptr->first_son = mkdir_create_Instance_ptr;
      ++parameter_position;
    }
  }
  return 1LL;
}

此时发现void sub_13C8()函数又跳转

Tab键:反编译
在这里插入图片描述

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
最后得到的原void sub_13C8()函数

__int64 __fastcall sub_13C9(__int64 a1, const char *a2)
{
  while ( a1 )
  {
    if ( !strcmp((const char *)(a1 + 4), a2) )
      return 0LL;
    a1 = *(_QWORD *)(a1 + 40);
  }
  return 1LL;
}

注意

当一个函数分析有点棘手时可以查看其他引用该函数的地方

修改后的__int64 __fastcall command_cat(const char **args)

__int64 __fastcall command_cat(const char **args)
{
  unsigned __int64 high_parament_length_16; // rax
  void *v2; // rsp
  _BYTE v4[8]; // [rsp+8h] [rbp-70h] BYREF
  const char **args_save; // [rsp+10h] [rbp-68h]
  char v6; // [rsp+1Fh] [rbp-59h]
  int parament_longest_length_more1; // [rsp+20h] [rbp-58h]
  int parameter_position; // [rsp+24h] [rbp-54h]
  SomeStruct *first_son; // [rsp+28h] [rbp-50h]
  __int64 parament_longest_length_more; // [rsp+30h] [rbp-48h]
  char *cat_file_name; // [rsp+38h] [rbp-40h]
  unsigned __int64 v12; // [rsp+40h] [rbp-38h]

  args_save = args;
  v12 = __readfsqword(0x28u);
  parameter_position = 0;
  v6 = 0;
  parament_longest_length_more1 = 0;
  first_son = 0LL;

  while ( args_save[++parameter_position] )
  {
    if ( strlen(args_save[parameter_position]) > parament_longest_length_more1 )
      parament_longest_length_more1 = strlen(args_save[parameter_position]) + 1;
  }

  parament_longest_length_more = parament_longest_length_more1 - 1LL;
  high_parament_length_16 = 16 * ((parament_longest_length_more1 + 15LL) / 0x10uLL);
  while ( v4 != &v4[-(high_parament_length_16 & 0xFFFFFFFFFFFFF000LL)] )
    ;
  v2 = alloca(high_parament_length_16 & 0xFFF);

  if ( (high_parament_length_16 & 0xFFF) != 0 )
    *&v4[(high_parament_length_16 & 0xFFF) - 8] = *&v4[(high_parament_length_16 & 0xFFF) - 8];
  cat_file_name = v4;                           // 上面都没啥用,v2,v4后面都没用到

  parameter_position = 1;



  if ( !args_save[1] )
    fwrite("mybash: missing operand\n", 1uLL, 0x18uLL, stderr);

  while ( args_save[parameter_position] )
  {
    first_son = current_directory_ptr->first_son;
    strcpy(cat_file_name, args_save[parameter_position]);

    while ( first_son )
    {
      if ( !strcmp(cat_file_name, first_son->file_name) )
      {
        if ( first_son->file_content_ptr )
          puts(first_son->file_content_ptr);
        v6 = 1;
        break;
      }
      first_son = first_son->next_ptr;
    }

    if ( v6 != 1 )
      fprintf(stderr, "mybash: %s: No such file or directory\n", args_save[parameter_position]);
    ++parameter_position;
  }

  return 1LL;
}

修改后的__int64 __fastcall command_rm(const char **args)

__int64 __fastcall command_rm(const char **args)
{
  // [COLLAPSED LOCAL DECLARATIONS. PRESS KEYPAD CTRL-"+" TO EXPAND]

  parameter_position = 1;
  if ( !args[1] )
    fwrite("mybash: missing operand\n", 1uLL, 0x18uLL, stderr);
  while ( args[parameter_position] )
  {
    son_file = current_directory_ptr->first_son;
    success_flag = 0;
    while ( son_file )
    {
      if ( !strcmp(son_file->file_name, args[parameter_position]) )
      {
        success_flag = 1;
        if ( IsFile(son_file) )
        {
          memset(son_file->file_name, 0, sizeof(son_file->file_name));
          if ( son_file->file_content_ptr )
            free(son_file->file_content_ptr);
          SomeStruct::unlink_file(son_file);
        }
        else
        {
          fprintf(stderr, "mybash: '%s': Is a directory\n", args[parameter_position]);
        }
        break;
      }
      son_file = son_file->next_ptr;
    }
    if ( success_flag != 1 )
      fprintf(stderr, "mybash: '%s': No such file or directory\n", args[parameter_position]);
    ++parameter_position;
  }
  return 1LL;
}

修改后的__int64 __fastcall command_echo(char **args)

__int64 __fastcall command_echo(char **args)
{
  SomeStruct *v2; // rbx
  SomeStruct *v3; // rbx
  int parameter_position; // [rsp+14h] [rbp-3Ch]
  int i; // [rsp+14h] [rbp-3Ch]
  int content_length; // [rsp+18h] [rbp-38h]
  int last_parameter_position; // [rsp+1Ch] [rbp-34h]
  int input_content_length; // [rsp+24h] [rbp-2Ch]
  SomeStruct *current_son_file; // [rsp+28h] [rbp-28h] BYREF
  const char *last_parameter_ptr; // [rsp+30h] [rbp-20h]
  unsigned __int64 v11; // [rsp+38h] [rbp-18h]

  v11 = __readfsqword(0x28u);
  parameter_position = 0;
  if ( args[1] )
  {
    do
      ++parameter_position;
    while ( args[parameter_position] );

    last_parameter_position = parameter_position - 1;
    if ( Is_No_Echo_to_File(args[parameter_position - 2]) )
    {
      for ( i = 1; i < last_parameter_position; ++i )
        printf(args[i]);
      puts(args[last_parameter_position]);
      return 1LL;
    }
    else
    {
      current_son_file = current_directory_ptr->first_son;
      last_parameter_ptr = args[last_parameter_position];
      if ( Is_Exist_File(&current_son_file, last_parameter_ptr) != 1 )
      {
        fprintf(stderr, "mybash: %s: No such file\n", last_parameter_ptr);
        return 1LL;
      }
      else if ( IsFile(current_son_file) )
      {
        if ( current_son_file->file_content_ptr )
        {
          content_length = SomeStruct::Get_Content_length(current_son_file->file_content_ptr);
        }
        else
        {
          content_length = 0x1F0;
          v2 = current_son_file;
          v2->file_content_ptr = malloc(0x1F0uLL);
          if ( !current_son_file->file_content_ptr )
            _exit(0);
        }

        input_content_length = strlen(args[last_parameter_position - 2]);
        while ( input_content_length > content_length )
          content_length += 0x1F0;

        if ( content_length > SomeStruct::Get_Content_length(current_son_file->file_content_ptr) )
        {
          v3 = current_son_file;
          v3->file_content_ptr = realloc(current_son_file->file_content_ptr, content_length);
        }
        strncpy(current_son_file->file_content_ptr, args[last_parameter_position - 2], input_content_length);
        return 1LL;
      }
      else
      {
        fprintf(stderr, "mybash: %s: Is a directory\n", last_parameter_ptr);
        return 1LL;
      }
    }
  }
  else
  {
    putchar(10);
    return 1LL;
  }
}

修改后的__int64 __fastcall command_cd(char **arg)

__int64 __fastcall command_cd(char **arg)
{
  size_t dest_length; // rbx
  size_t current_file_name_length; // rax
  int main_save_instance_ptr_file_name_length; // [rsp+18h] [rbp-38h]
  const char *after_dlim_para; // [rsp+20h] [rbp-30h]
  SomeStruct *current_file; // [rsp+28h] [rbp-28h]
  char delim[2]; // [rsp+36h] [rbp-1Ah] BYREF
  unsigned __int64 v8; // [rsp+38h] [rbp-18h]

  v8 = __readfsqword(0x28u);
  if ( arg[1] )
  {
    if ( arg[2] )
    {
      fwrite("mybash: too many arguments\n", 1uLL, 0x1BuLL, stderr);
    }
    else
    {
      strcpy(delim, "/");
      for ( after_dlim_para = strtok(arg[1], delim); after_dlim_para; after_dlim_para = strtok(0LL, delim) )
      {
        if ( strcmp(after_dlim_para, ".") )
        {
          if ( !strcmp(after_dlim_para, "..") )
          {
            if ( current_directory_ptr->parent )
            {
              main_save_instance_ptr_file_name_length = strlen(current_directory_ptr->file_name);
              current_directory_path[(strlen(current_directory_path) - 1 - main_save_instance_ptr_file_name_length)] = 0;
              current_directory_ptr = current_directory_ptr->parent;// 当前目录更新为之前目录的父目录
            }
          }
          else
          {
            current_file = current_directory_ptr->first_son;
            if ( SomeStruct::File_Not_Eixst(current_file, after_dlim_para) )
            {
              fprintf(stderr, "mybash: %s: No such file or directory\n", after_dlim_para);
              return 1LL;
            }

            while ( current_file && strcmp(current_file->file_name, after_dlim_para) )
              current_file = current_file->next_ptr;
            if ( !SomeStruct::IsDirectory(current_file) )
            {
              fwrite("something wrong happened\n", 1uLL, 0x19uLL, stderr);
              return 1LL;
            }
            current_directory_ptr = current_file;
            dest_length = strlen(current_directory_path);

            if ( dest_length + strlen(current_file->file_name) + 1 <= 0x4F )
            {
              current_file_name_length = strlen(current_file->file_name);
              strncat(current_directory_path, current_file->file_name, current_file_name_length);
              *&current_directory_path[strlen(current_directory_path)] = 47;
            }
          }
        }
      }
    }
  }
  else
  {
    fwrite("mybash: expected argument\n", 1uLL, 0x1AuLL, stderr);
  }
  return 1LL;
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

看星猩的柴狗

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值