'.', 'd', 'e', 'b', 'u', 'g', '_', 'l', 'i', 'n', 'e', 0, /* 52 */
        '.', 'd', 'e', 'b', 'u', 'g', '_', 'i', 'n', 'f', 'o', 0, /* 64 */
        '.', 'd', 'e', 'b', 'u', 'g', '_', 'a', 'b', 'b', 'r', 'e', 'v', 0, /* 76 */
+       '.', 'e', 'h', '_', 'f', 'r', 'a', 'm', 'e', '_', 'h', 'd', 'r', 0, /* 90 */
+       '.', 'e', 'h', '_', 'f', 'r', 'a', 'm', 'e', 0, /* 104 */
 };
 
 static struct buildid_note {
 }
 #endif
 
+static int
+jit_add_eh_frame_info(Elf *e, void* unwinding, uint64_t unwinding_header_size,
+                     uint64_t unwinding_size, uint64_t base_offset)
+{
+       Elf_Data *d;
+       Elf_Scn *scn;
+       Elf_Shdr *shdr;
+       uint64_t unwinding_table_size = unwinding_size - unwinding_header_size;
+
+       /*
+        * setup eh_frame section
+        */
+       scn = elf_newscn(e);
+       if (!scn) {
+               warnx("cannot create section");
+               return -1;
+       }
+
+       d = elf_newdata(scn);
+       if (!d) {
+               warnx("cannot get new data");
+               return -1;
+       }
+
+       d->d_align = 8;
+       d->d_off = 0LL;
+       d->d_buf = unwinding;
+       d->d_type = ELF_T_BYTE;
+       d->d_size = unwinding_table_size;
+       d->d_version = EV_CURRENT;
+
+       shdr = elf_getshdr(scn);
+       if (!shdr) {
+               warnx("cannot get section header");
+               return -1;
+       }
+
+       shdr->sh_name = 104;
+       shdr->sh_type = SHT_PROGBITS;
+       shdr->sh_addr = base_offset;
+       shdr->sh_flags = SHF_ALLOC;
+       shdr->sh_entsize = 0;
+
+       /*
+        * setup eh_frame_hdr section
+        */
+       scn = elf_newscn(e);
+       if (!scn) {
+               warnx("cannot create section");
+               return -1;
+       }
+
+       d = elf_newdata(scn);
+       if (!d) {
+               warnx("cannot get new data");
+               return -1;
+       }
+
+       d->d_align = 4;
+       d->d_off = 0LL;
+       d->d_buf = unwinding + unwinding_table_size;
+       d->d_type = ELF_T_BYTE;
+       d->d_size = unwinding_header_size;
+       d->d_version = EV_CURRENT;
+
+       shdr = elf_getshdr(scn);
+       if (!shdr) {
+               warnx("cannot get section header");
+               return -1;
+       }
+
+       shdr->sh_name = 90;
+       shdr->sh_type = SHT_PROGBITS;
+       shdr->sh_addr = base_offset + unwinding_table_size;
+       shdr->sh_flags = SHF_ALLOC;
+       shdr->sh_entsize = 0;
+
+       return 0;
+}
+
 /*
  * fd: file descriptor open for writing for the output file
  * load_addr: code load address (could be zero, just used for buildid)
 int
 jit_write_elf(int fd, uint64_t load_addr, const char *sym,
              const void *code, int csize,
-             void *debug __maybe_unused, int nr_debug_entries __maybe_unused)
+             void *debug __maybe_unused, int nr_debug_entries __maybe_unused,
+             void *unwinding, uint64_t unwinding_header_size, uint64_t unwinding_size)
 {
        Elf *e;
        Elf_Data *d;
        Elf_Scn *scn;
        Elf_Ehdr *ehdr;
        Elf_Shdr *shdr;
+       uint64_t eh_frame_base_offset;
        char *strsym = NULL;
        int symlen;
        int retval = -1;
        ehdr->e_type = ET_DYN;
        ehdr->e_entry = GEN_ELF_TEXT_OFFSET;
        ehdr->e_version = EV_CURRENT;
-       ehdr->e_shstrndx= 2; /* shdr index for section name */
+       ehdr->e_shstrndx= unwinding ? 4 : 2; /* shdr index for section name */
 
        /*
         * setup text section
        shdr->sh_flags = SHF_EXECINSTR | SHF_ALLOC;
        shdr->sh_entsize = 0;
 
+       /*
+        * Setup .eh_frame_hdr and .eh_frame
+        */
+       if (unwinding) {
+               eh_frame_base_offset = ALIGN_8(GEN_ELF_TEXT_OFFSET + csize);
+               retval = jit_add_eh_frame_info(e, unwinding,
+                                              unwinding_header_size, unwinding_size,
+                                              eh_frame_base_offset);
+               if (retval)
+                       goto error;
+       }
+
        /*
         * setup section headers string table
         */
        shdr->sh_type = SHT_SYMTAB;
        shdr->sh_flags = 0;
        shdr->sh_entsize = sizeof(Elf_Sym);
-       shdr->sh_link = 4; /* index of .strtab section */
+       shdr->sh_link = unwinding ? 6 : 4; /* index of .strtab section */
 
        /*
         * setup symbols string table
 
             const void *code,
             int csize,
             void *debug,
-            int nr_debug_entries)
+            int nr_debug_entries,
+            void *unwinding,
+            uint32_t unwinding_header_size,
+            uint32_t unwinding_size)
 {
        int ret, fd;
 
                return -1;
        }
 
-        ret = jit_write_elf(fd, code_addr, sym, (const void *)code, csize, debug, nr_debug_entries);
+       ret = jit_write_elf(fd, code_addr, sym, (const void *)code, csize, debug, nr_debug_entries,
+                           unwinding, unwinding_header_size, unwinding_size);
 
         close(fd);
 
 
        size = PERF_ALIGN(size, sizeof(u64));
        uaddr = (uintptr_t)code;
-       ret = jit_emit_elf(filename, sym, addr, (const void *)uaddr, csize, jd->debug_data, jd->nr_debug_entries);
+       ret = jit_emit_elf(filename, sym, addr, (const void *)uaddr, csize, jd->debug_data, jd->nr_debug_entries,
+                          jd->unwinding_data, jd->eh_frame_hdr_size, jd->unwinding_size);
 
        if (jd->debug_data && jd->nr_debug_entries) {
                free(jd->debug_data);