def create(offset, size, name, **kwds): '''Create a segment at /offset/ and /size/ and name it /name/ /bits/ can be used to specify the bit size of the segment /comb/ can be used to specify any flags (idaapi.sc*) /align/ can be used to specify paragraph alignment (idaapi.sa*) /org/ specifies the origin of the segment (must be paragraph aligned due to ida) ''' s = idaapi.get_segm_by_name(name) if s is not None: logging.fatal( "segment.create(%x, %x, %r, %r) : a segment with the specified name already exists : %s", offset, size, name, kwds, name) return None bits = kwds.get( 'bits', 32 if idaapi.getseg(offset) is None else idaapi.getseg(offset). abits()) # FIXME: use disassembler default bit length instead of 32 if bits == 16: ## create a selector with the requested origin org = kwds.get('org', 0) if org & 0xf > 0: logging.fatal( "segment.create(%x, %x, %r, %r) : origin (.org) is not aligned to the size of a paragraph (0x10):%x", offset, size, name, kwds, org) return None para = offset / 16 sel = idaapi.allocate_selector(para) idaapi.set_selector(sel, (para - kwds.get('org', 0) / 16) & 0xffffffff) else: ## auto-create a selector for everything else sel = idaapi.setup_selector( kwds['selector'] ) if 'selector' in kwds else idaapi.find_free_selector() # create segment. ripped from idc s = idaapi.segment_t() s.startEA = offset s.endEA = offset + size s.sel = sel s.bitness = {16: 0, 32: 1, 64: 2}[bits] s.comb = kwds.get('comb', idaapi.scPub) # public s.align = kwds.get('align', idaapi.saRelByte) # paragraphs res = idaapi.add_segm_ex(s, name, "", idaapi.ADDSEG_NOSREG | idaapi.ADDSEG_SPARSE) if res == 0: logging.warn( "segment.create(%x, %x, %r, %r) : unable to add a new segment", offset, size, name, kwds) res = idaapi.del_selector(sel) #assert res != 0 return None return s
def create(offset, size, name, **kwds): '''Create a segment at /offset/ and /size/ and name it /name/ /bits/ can be used to specify the bit size of the segment /comb/ can be used to specify any flags (idaapi.sc*) /align/ can be used to specify paragraph alignment (idaapi.sa*) /org/ specifies the origin of the segment (must be paragraph aligned due to ida) ''' s = idaapi.get_segm_by_name(name) if s is not None: logging.fatal("segment.create(%x, %x, %r, %r) : a segment with the specified name already exists : %s", offset, size, name, kwds, name) return None bits = kwds.get( 'bits', 32 if idaapi.getseg(offset) is None else idaapi.getseg(offset).abits()) # FIXME: use disassembler default bit length instead of 32 if bits == 16: ## create a selector with the requested origin org = kwds.get('org',0) if org&0xf > 0: logging.fatal("segment.create(%x, %x, %r, %r) : origin (.org) is not aligned to the size of a paragraph (0x10):%x", offset, size, name, kwds, org) return None para = offset/16 sel = idaapi.allocate_selector(para) idaapi.set_selector(sel, (para-kwds.get('org',0)/16)&0xffffffff) else: ## auto-create a selector for everything else sel = idaapi.setup_selector(kwds['selector']) if 'selector' in kwds else idaapi.find_free_selector() # create segment. ripped from idc s = idaapi.segment_t() s.startEA = offset s.endEA = offset+size s.sel = sel s.bitness = {16:0,32:1,64:2}[bits] s.comb = kwds.get('comb', idaapi.scPub) # public s.align = kwds.get('align', idaapi.saRelByte) # paragraphs res = idaapi.add_segm_ex(s, name, "", idaapi.ADDSEG_NOSREG|idaapi.ADDSEG_SPARSE) if res == 0: logging.warn("segment.create(%x, %x, %r, %r) : unable to add a new segment", offset, size, name, kwds) res = idaapi.del_selector(sel) #assert res != 0 return None return s
def new(offset, size, name, **kwds): """Create a segment at ``offset`` with ``size`` and name it according to ``name``. ``bits`` can be used to specify the bit size of the segment ``comb`` can be used to specify any flags (idaapi.sc*) ``align`` can be used to specify paragraph alignment (idaapi.sa*) ``org`` specifies the origin of the segment (must be paragraph aligned due to ida) """ s = idaapi.get_segm_by_name(name) if s is not None: logging.fatal("{:s}.new({:x}, {:x}, {!r}, {!r}) : a segment with the specified name already exists : {:s}".format(__name__, offset, size, name, kwds, name)) return None bits = kwds.get( 'bits', 32 if idaapi.getseg(offset) is None else idaapi.getseg(offset).abits()) # FIXME: use disassembler default bit length instead of 32 if bits == 16: ## create a selector with the requested origin org = kwds.get('org',0) if org&0xf > 0: logging.fatal("{:s}.new({:x}, {:x}, {!r}, {!r}) : origin (.org) is not aligned to the size of a paragraph (0x10) : {:x}".format(__name__, offset, size, name, kwds, org)) return None para = offset/16 sel = idaapi.allocate_selector(para) idaapi.set_selector(sel, (para-kwds.get('org',0)/16)&0xffffffff) else: ## auto-create a selector for everything else sel = idaapi.setup_selector(kwds['selector']) if 'selector' in kwds else idaapi.find_free_selector() # create segment. ripped from idc s = idaapi.segment_t() s.startEA = offset s.endEA = offset+size s.sel = sel s.bitness = {16:0,32:1,64:2}[bits] s.comb = kwds.get('comb', idaapi.scPub) # public s.align = kwds.get('align', idaapi.saRelByte) # paragraphs res = idaapi.add_segm_ex(s, name, "", idaapi.ADDSEG_NOSREG|idaapi.ADDSEG_SPARSE) if res == 0: logging.warn("{:s}.new({:x}, {:x}, {!r}, {!r}) : unable to add a new segment".format(__name__, offset, size, name, kwds)) res = idaapi.del_selector(sel) #assert res != 0 return None return s
def new(offset, size, name, **kwds): """Create a segment at `offset` with `size` and name it according to `name`. The keyword `bits` can be used to specify the bit size of the segment The keyword `comb` can be used to specify any flags (idaapi.sc*) The keyword `align` can be used to specify paragraph alignment (idaapi.sa*) The keyword `org` specifies the origin of the segment (must be paragraph aligned due to ida) """ res = utils.string.to(name) # find the segment according to the name specified by the user seg = idaapi.get_segm_by_name(res) if seg is not None: raise E.DuplicateItemError( u"{:s}.new({:#x}, {:+#x}, \"{:s}\"{:s}) : A segment with the specified name (\"{:s}\") already exists." .format( __name__, offset, size, utils.string.escape(name, '"'), u", {:s}".format(utils.string.kwargs(kwds)) if kwds else '', utils.string.escape(name, '"'))) # FIXME: use disassembler default bit length instead of 32 bits = kwds.get( 'bits', 32 if idaapi.getseg(offset) is None else idaapi.getseg(offset).abits()) ## create a selector with the requested origin if bits == 16: org = kwds.get('org', 0) if org & 0xf > 0: raise E.InvalidTypeOrValueError( u"{:s}.new({:#x}, {:+#x}, {!r}{:s}) : The specified origin ({:#x}) is not aligned to the size of a paragraph (0x10)." .format( __name__, offset, size, name, u", {:s}".format( utils.string.kwargs(kwds)) if kwds else '', org)) para = offset // 16 sel = idaapi.allocate_selector(para) idaapi.set_selector(sel, (para - kwds.get('org', 0) // 16) & 0xffffffff) ## if the user specified a selector, then use it elif 'sel' in kwds or 'selector' in kwds: sel = kwds.get('sel', kwds.get('selector', idaapi.find_free_selector())) ## choose the paragraph size defined by the user elif 'para' in kwds or 'paragraphs' in kwds: para = kwds.get('paragraph', kwds.get('para', 1)) sel = idaapi.setup_selector(para) ## find a selector that is 1 paragraph size, elif idaapi.get_selector_qty(): sel = idaapi.find_selector(1) # otherwise find a free one and set it. else: sel = idaapi.find_free_selector() idaapi.set_selector(sel, 1) # populate the segment_t for versions of IDA prior to 7.0 if idaapi.__version__ < 7.0: seg = idaapi.segment_t() seg.startEA, seg.endEA = offset, offset + size # now for versions of IDA 7.0 and newer else: seg = idaapi.segment_t() seg.start_ea, seg.end_ea = offset, offset + size # assign the rest of the necessary attributes seg.sel = sel seg.bitness = {16: 0, 32: 1, 64: 2}[bits] seg.comb = kwds.get('comb', idaapi.scPub) # public seg.align = kwds.get('align', idaapi.saRelByte) # paragraphs # now we can add our segment_t to the database res = utils.string.to(name) ok = idaapi.add_segm_ex(seg, res, "", idaapi.ADDSEG_NOSREG | idaapi.ADDSEG_SPARSE) if not ok: ok = idaapi.del_selector(sel) if not ok: logging.warning( u"{:s}.new({:#x}, {:+#x}, {!r}{:s}) : Unable to delete the created selector ({:#x}) for the new segment." .format( __name__, offset, size, name, u", {:s}".format( utils.string.kwargs(kwds)) if kwds else '', sel)) raise E.DisassemblerError( u"{:s}.new({:#x}, {:+#x}, {!r}{:s}) : Unable to add a new segment." .format( __name__, offset, size, name, u", {:s}".format(utils.string.kwargs(kwds)) if kwds else '')) return seg
def load_file(li, neflags, format): idaapi.set_processor_type('xap2csr', idaapi.SETPROC_ALL | idaapi.SETPROC_FATAL) li.seek(0) lines = li.read(li.size()).split('\n') segs = {} for seg in ('code', 'data'): segs[seg] = {'chunks': [], 'syms': []} def handle_line(line): raise ValueError('got non-commented line before title: %r' % (line, )) for line in lines: #print repr(line) line = line.strip() if not line: continue if not line.startswith('// '): line = re.sub('\s*//.*', '', line) handle_line(line) continue m = re.match('^// Title +: "(Code|Constant|Symbol) Table"', line) if not m: continue kind = m.group(1) if kind in ('Code', 'Constant'): chunks = segs['code' if kind == 'Code' else 'data']['chunks'] if chunks != []: raise ValueError('more than one %s table in file' % (kind, )) cur_addr_box = [None] cur_chunk_box = [None] def handle_line(line): m = re.match('^@([0-9A-Fa-f]+)\s+([0-9A-Fa-f]{4})$', line) if not m: raise ValueError('unrecognized seg line: %r' % (line, )) addr, word = [int(x, 16) for x in m.groups()] cur_addr, cur_chunk = cur_addr_box[0], cur_chunk_box[0] if cur_addr is None or addr > cur_addr: cur_chunk = cur_chunk_box[0] = [] chunks.append((addr, cur_chunk)) elif addr < cur_addr: raise ValueError( 'going backwards with addresses (cur_addr=0x%x): %r' % ( cur_addr, line, )) cur_chunk.append(word) cur_addr_box[0] = addr + 1 else: assert kind == 'Symbol' cur_syms_box = [None] def handle_line(line): if line in ('.CODE', '.DATA'): cur_syms_box[0] = segs[line[1:].lower()]['syms'] else: m = re.match('^([^,]+), ([0-9a-fA-F]+)*$', line) if not m: raise ValueError('unknown symbol line: %r' % (line, )) cur_syms = cur_syms_box[0] if cur_syms is None: raise ValueError('symbols without a segment: %r' % (line, )) cur_syms.append((int(m.group(2), 16), m.group(1))) # (addr, name) for (segname, info) in segs.iteritems(): kind = {'code': 0, 'data': 1}[segname] base_addr = (0, 0x1000000)[kind] if segname == 'code' and info['chunks'] == [] and info['syms'] == []: continue if not idaapi.set_selector(kind + 1, base_addr >> 4): raise Exception("couldn't set selector for segment %s" % (name, )) for addr, chunk in info['chunks']: seg = idaapi.segment_t() seg.startEA = base_addr + addr seg.endEA = base_addr + addr + len(chunk) seg.bitness = 1 # 32-bit (we can have more than 16 bits of code, so just use for both) seg.sel = kind + 1 name = '%s_%x' % (segname, addr) klass = segname.upper() #print '%s from %x to %x' % (name, seg.startEA, seg.endEA) if not idaapi.add_segm_ex(seg, name, klass, ADDSEG_NOSREG): raise Exception("couldn't add segment %s" % (name, )) ea = seg.startEA for word in chunk: idaapi.put_byte(ea, word) ea += 1 if segname == 'code': idaapi.autoMark(seg.startEA, AU_CODE) if segname == 'data': # fill in the remaining area with BSS spaces = zip( [0] + [addr + len(chunk) for (addr, chunk) in info['chunks']], [addr for (addr, chunk) in info['chunks']] + [0x10000]) for start, end in spaces: if end - start < 0x10: continue assert end > start seg = idaapi.segment_t() seg.startEA = base_addr + start seg.endEA = base_addr + end seg.bitness = 1 seg.sel = kind + 1 name = 'bss_%x' % (start, ) #print '%s from %x to %x' % (name, seg.startEA, seg.endEA) if not idaapi.add_segm_ex( seg, name, 'BSS', idaapi.ADDSEG_SPARSE | ADDSEG_NOSREG): raise Exception("couldn't add segment %s" % (name, )) return 1
def new(offset, size, name, **kwds): """Create a segment at `offset` with `size` and name it according to `name`. The keyword `bits` can be used to specify the bit size of the segment The keyword `comb` can be used to specify any flags (idaapi.sc*) The keyword `align` can be used to specify paragraph alignment (idaapi.sa*) The keyword `org` specifies the origin of the segment (must be paragraph aligned due to ida) """ seg = idaapi.get_segm_by_name(name) if seg is not None: raise NameError( "{:s}.new({:#x}, {:+#x}, {!r}{:s}) : A segment with the specified name ({!r}) already exists." .format( __name__, offset, size, name, ", {:s}".format(', '.join( "{:s}={!r}".format(k, v) for k, v in kwds.iteritems())) if kwds else '', name)) bits = kwds.get( 'bits', 32 if idaapi.getseg(offset) is None else idaapi.getseg(offset). abits()) # FIXME: use disassembler default bit length instead of 32 ## create a selector with the requested origin if bits == 16: org = kwds.get('org', 0) if org & 0xf > 0: raise E.InvalidTypeOrValueError( "{:s}.new({:#x}, {:+#x}, {!r}{:s}) : The specified origin ({:#x}) is not aligned to the size of a paragraph (0x10)." .format( __name__, offset, size, name, ", {:s}".format(', '.join( "{:s}={!r}".format(k, v) for k, v in kwds.iteritems())) if kwds else '', org)) para = offset / 16 sel = idaapi.allocate_selector(para) idaapi.set_selector(sel, (para - kwds.get('org', 0) / 16) & 0xffffffff) ## if the user specified a selector, then use it elif 'sel' in kwds or 'selector' in kwds: sel = kwds.get('sel', kwds.get('selector', idaapi.find_free_selector())) ## choose the paragraph size defined by the user elif 'para' in kwds or 'paragraphs' in kwds: para = kwds.get('paragraph', kwds.get('para', 1)) sel = idaapi.setup_selector(res) ## find a selector that is 1 paragraph size, elif idaapi.get_selector_qty(): sel = idaapi.find_selector(1) # otherwise find a free one and set it. else: sel = idaapi.find_free_selector() idaapi.set_selector(sel, 1) # create segment. ripped from idc seg = idaapi.segment_t() seg.startEA = offset seg.endEA = offset + size seg.sel = sel seg.bitness = {16: 0, 32: 1, 64: 2}[bits] seg.comb = kwds.get('comb', idaapi.scPub) # public seg.align = kwds.get('align', idaapi.saRelByte) # paragraphs ok = idaapi.add_segm_ex(seg, name, "", idaapi.ADDSEG_NOSREG | idaapi.ADDSEG_SPARSE) if not ok: ok = idaapi.del_selector(sel) if not ok: logging.warn( "{:s}.new({:#x}, {:+#x}, {!r}{:s}) : Unable to delete the created selector ({:#x}) for the new segment." .format( __name__, offset, size, name, ", {:s}".format(', '.join( "{:s}={!r}".format(k, v) for k, v in kwds.iteritems())) if kwds else '', sel)) raise E.DisassemblerError( "{:s}.new({:#x}, {:+#x}, {!r}{:s}) : Unable to add a new segment.". format( __name__, offset, size, name, ", {:s}".format(', '.join( "{:s}={!r}".format(k, v) for k, v in kwds.iteritems())) if kwds else '')) return seg
def new(offset, size, name, **kwds): """Create a segment at ``offset`` with ``size`` and name it according to ``name``. The keyword ``bits`` can be used to specify the bit size of the segment The keyword ``comb`` can be used to specify any flags (idaapi.sc*) The keyword ``align`` can be used to specify paragraph alignment (idaapi.sa*) The keyword ``org`` specifies the origin of the segment (must be paragraph aligned due to ida) """ s = idaapi.get_segm_by_name(name) if s is not None: logging.fatal( "{:s}.new({:#x}, {:+#x}, {!r}, {!r}) : A segment with the specified name ({!r}) already exists." .format(__name__, offset, size, name, kwds, name)) return None bits = kwds.get( 'bits', 32 if idaapi.getseg(offset) is None else idaapi.getseg(offset). abits()) # FIXME: use disassembler default bit length instead of 32 ## create a selector with the requested origin if bits == 16: org = kwds.get('org', 0) if org & 0xf > 0: logging.fatal( "{:s}.new({:#x}, {:+#x}, {!r}, {!r}) : The origin ({:#x}) is not aligned to the size of a paragraph (0x10)." .format(__name__, offset, size, name, kwds, org)) return None para = offset / 16 sel = idaapi.allocate_selector(para) idaapi.set_selector(sel, (para - kwds.get('org', 0) / 16) & 0xffffffff) ## if the user specified a selector, then use it elif 'sel' in kwds or 'selector' in kwds: sel = kwds.get('sel', kwds.get('selector', idaapi.find_free_selector())) ## choose the paragraph size defined by the user elif 'para' in kwds or 'paragraphs' in kwds: para = kwds.get('paragraph', kwds.get('para', 1)) sel = idaapi.setup_selector(res) ## find a selector that is 1 paragraph size, elif idaapi.get_selector_qty(): sel = idaapi.find_selector(1) # otherwise find a free one and set it. else: sel = idaapi.find_free_selector() idaapi.set_selector(sel, 1) # create segment. ripped from idc s = idaapi.segment_t() s.startEA = offset s.endEA = offset + size s.sel = sel s.bitness = {16: 0, 32: 1, 64: 2}[bits] s.comb = kwds.get('comb', idaapi.scPub) # public s.align = kwds.get('align', idaapi.saRelByte) # paragraphs res = idaapi.add_segm_ex(s, name, "", idaapi.ADDSEG_NOSREG | idaapi.ADDSEG_SPARSE) if res == 0: logging.warn( "{:s}.new({:#x}, {:+#x}, {!r}, {!r}) : Unable to add a new segment." .format(__name__, offset, size, name, kwds)) res = idaapi.del_selector(sel) #assert res != 0 return None return s
def load_file(li, neflags, format): idaapi.set_processor_type('xap2csr', idaapi.SETPROC_ALL | idaapi.SETPROC_FATAL) li.seek(0) lines = li.read(li.size()).split('\n') segs = {} for seg in ('code', 'data'): segs[seg] = {'chunks': [], 'syms': []} def handle_line(line): raise ValueError('got non-commented line before title: %r' % (line,)) for line in lines: #print repr(line) line = line.strip() if not line: continue if not line.startswith('// '): line = re.sub('\s*//.*', '', line) handle_line(line) continue m = re.match('^// Title +: "(Code|Constant|Symbol) Table"', line) if not m: continue kind = m.group(1) if kind in ('Code', 'Constant'): chunks = segs['code' if kind == 'Code' else 'data']['chunks'] if chunks != []: raise ValueError('more than one %s table in file' % (kind,)) cur_addr_box = [None] cur_chunk_box = [None] def handle_line(line): m = re.match('^@([0-9A-Fa-f]+)\s+([0-9A-Fa-f]{4})$', line) if not m: raise ValueError('unrecognized seg line: %r' % (line,)) addr, word = [int(x, 16) for x in m.groups()] cur_addr, cur_chunk = cur_addr_box[0], cur_chunk_box[0] if cur_addr is None or addr > cur_addr: cur_chunk = cur_chunk_box[0] = [] chunks.append((addr, cur_chunk)) elif addr < cur_addr: raise ValueError('going backwards with addresses (cur_addr=0x%x): %r' % (cur_addr, line,)) cur_chunk.append(word) cur_addr_box[0] = addr + 1 else: assert kind == 'Symbol' cur_syms_box = [None] def handle_line(line): if line in ('.CODE', '.DATA'): cur_syms_box[0] = segs[line[1:].lower()]['syms'] else: m = re.match('^([^,]+), ([0-9a-fA-F]+)*$', line) if not m: raise ValueError('unknown symbol line: %r' % (line,)) cur_syms = cur_syms_box[0] if cur_syms is None: raise ValueError('symbols without a segment: %r' % (line,)) cur_syms.append((int(m.group(2), 16), m.group(1))) # (addr, name) for (segname, info) in segs.iteritems(): kind = {'code': 0, 'data': 1}[segname] base_addr = (0, 0x1000000)[kind] if segname == 'code' and info['chunks'] == [] and info['syms'] == []: continue if not idaapi.set_selector(kind + 1, base_addr >> 4): raise Exception("couldn't set selector for segment %s" % (name,)) for addr, chunk in info['chunks']: seg = idaapi.segment_t() seg.startEA = base_addr + addr seg.endEA = base_addr + addr + len(chunk) seg.bitness = 1 # 32-bit (we can have more than 16 bits of code, so just use for both) seg.sel = kind + 1 name = '%s_%x' % (segname, addr) klass = segname.upper() #print '%s from %x to %x' % (name, seg.startEA, seg.endEA) if not idaapi.add_segm_ex(seg, name, klass, ADDSEG_NOSREG): raise Exception("couldn't add segment %s" % (name,)) ea = seg.startEA for word in chunk: idaapi.put_byte(ea, word) ea += 1 if segname == 'code': idaapi.autoMark(seg.startEA, AU_CODE) if segname == 'data': # fill in the remaining area with BSS spaces = zip([0] + [addr+len(chunk) for (addr, chunk) in info['chunks']], [addr for (addr, chunk) in info['chunks']] + [0x10000]) for start, end in spaces: if end - start < 0x10: continue assert end > start seg = idaapi.segment_t() seg.startEA = base_addr + start seg.endEA = base_addr + end seg.bitness = 1 seg.sel = kind + 1 name = 'bss_%x' % (start,) #print '%s from %x to %x' % (name, seg.startEA, seg.endEA) if not idaapi.add_segm_ex(seg, name, 'BSS', idaapi.ADDSEG_SPARSE | ADDSEG_NOSREG): raise Exception("couldn't add segment %s" % (name,)) return 1
def new(offset, size, name, **kwds): """Create a segment at `offset` with `size` and name it according to `name`. The keyword `bits` can be used to specify the bit size of the segment The keyword `comb` can be used to specify any flags (idaapi.sc*) The keyword `align` can be used to specify paragraph alignment (idaapi.sa*) The keyword `org` specifies the origin of the segment (must be paragraph aligned due to ida) """ res = utils.string.to(name) # find the segment according to the name specified by the user seg = idaapi.get_segm_by_name(res) if seg is not None: raise E.DuplicateItemError(u"{:s}.new({:#x}, {:+#x}, \"{:s}\"{:s}) : A segment with the specified name (\"{:s}\") already exists.".format(__name__, offset, size, utils.string.escape(name, '"'), u", {:s}".format(utils.string.kwargs(kwds)) if kwds else '', utils.string.escape(name, '"'))) # FIXME: use disassembler default bit length instead of 32 bits = kwds.get( 'bits', 32 if idaapi.getseg(offset) is None else idaapi.getseg(offset).abits()) ## create a selector with the requested origin if bits == 16: org = kwds.get('org',0) if org & 0xf > 0: raise E.InvalidTypeOrValueError(u"{:s}.new({:#x}, {:+#x}, {!r}{:s}) : The specified origin ({:#x}) is not aligned to the size of a paragraph (0x10).".format(__name__, offset, size, name, u", {:s}".format(utils.string.kwargs(kwds)) if kwds else '', org)) para = offset/16 sel = idaapi.allocate_selector(para) idaapi.set_selector(sel, (para-kwds.get('org',0)/16)&0xffffffff) ## if the user specified a selector, then use it elif 'sel' in kwds or 'selector' in kwds: sel = kwds.get('sel', kwds.get('selector', idaapi.find_free_selector())) ## choose the paragraph size defined by the user elif 'para' in kwds or 'paragraphs' in kwds: para = kwds.get('paragraph', kwds.get('para', 1)) sel = idaapi.setup_selector(para) ## find a selector that is 1 paragraph size, elif idaapi.get_selector_qty(): sel = idaapi.find_selector(1) # otherwise find a free one and set it. else: sel = idaapi.find_free_selector() idaapi.set_selector(sel, 1) # populate the segment_t using code ripped from the idc module seg = idaapi.segment_t() seg.startEA = offset seg.endEA = offset+size seg.sel = sel seg.bitness = {16:0,32:1,64:2}[bits] seg.comb = kwds.get('comb', idaapi.scPub) # public seg.align = kwds.get('align', idaapi.saRelByte) # paragraphs # now we can add our segment_t to the database res = utils.string.to(name) ok = idaapi.add_segm_ex(seg, res, "", idaapi.ADDSEG_NOSREG|idaapi.ADDSEG_SPARSE) if not ok: ok = idaapi.del_selector(sel) if not ok: logging.warn(u"{:s}.new({:#x}, {:+#x}, {!r}{:s}) : Unable to delete the created selector ({:#x}) for the new segment.".format(__name__, offset, size, name, u", {:s}".format(utils.string.kwargs(kwds)) if kwds else '', sel)) raise E.DisassemblerError(u"{:s}.new({:#x}, {:+#x}, {!r}{:s}) : Unable to add a new segment.".format(__name__, offset, size, name, u", {:s}".format(utils.string.kwargs(kwds)) if kwds else '')) return seg