Skip to content

_IO_proc_jumps

Bir popen stream'i (_IO_proc_jumps vtable) forge et; böylece close path'i (_IO_new_proc_close) attacker-kontrollü bir _IO_proc_file ve onun sakladığı pid üzerinde işler.

Mechanism

Note

popen(), bir struct _IO_proc_file — child pid ile genişletilmiş bir FILE — allocate eder ve _IO_proc_jumps vtable'ını kurar. Ayırt edici slot, _IO_new_proc_close'a eşlenen __close'tur: pclose/fclose'da global proc-file listesini gezer, entry'yi kaldırır ve saklanan pid üzerinde waitpid() yapar. proc-file (pid ve next link'i dahil) attacker-etkilenebilir libc/heap memory'sinde yaşadığı için, onu forge etmek attacker'ın close path'ini sürmesine izin verir — proc-file linked list'ini ve waitpid'e geçilen değeri manipüle eder. Forge edilmiş bir FILE'ın vtable'ını meşru _IO_proc_jumps'a işaret ettirmek onu 2.24 vtable range'i içinde tutar.

Walkthrough

Yapı (glibc libio/iopopen.c):

struct _IO_proc_file {
  struct _IO_FILE_plus file;
  pid_t pid;
  struct _IO_proc_file *next;
};
/* vtable slot of interest:  __close -> _IO_new_proc_close */

_IO_new_proc_close (kavramsal):

int _IO_new_proc_close (FILE *fp) {
  struct _IO_proc_file **ptr = &proc_file_chain;
  for (; *ptr != (_IO_proc_file *) fp; ptr = &(*ptr)->next)  /* list walk */
    ;
  *ptr = (*ptr)->next;                                       /* unlink     */
  do wait_status = waitpid (((_IO_proc_file *) fp)->pid, ...);/* uses pid   */
  ...
}

Abuse path'i:

  1. vtable = &_IO_proc_jumps (in range) ve seçilmiş bir next/pid ile bir _IO_proc_file forge et.
  2. Onu insert et (ya da proc_file_chain'i corrupt et); böylece list walk/unlink kontrollü bir pointer (*ptr = (*ptr)->next) yazar — unlink aracılığıyla kısıtlı bir write-where.
  3. fclose/pclose'u tetikle.

Warning

proc path'i _IO_str_jumps/_IO_wfile_jumps'tan daha az doğrudan silahlandırılabilir (temiz bir arbitrary call değil, bir list-unlink write ve waitpid etkisi verir); esas olarak yalnızca close path'i erişilebilir olduğunda alakalıdır.

Detection

  • popen tarafından oluşturulmamış bir proc-file üzerinde işleyen _IO_new_proc_close; corrupt edilmiş proc_file_chain.

Mitigation

  • glibc 2.24+ vtable range check'i; hardened FILE handling; full RELRO.

References