Skip to content
This repository has been archived by the owner on Oct 2, 2020. It is now read-only.

Added logic to fix-pins.py to shift off-grid pins to next grid line #9

Open
wants to merge 1 commit into
base: master
Choose a base branch
from
Open
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
223 changes: 142 additions & 81 deletions schlib/fix-pins.py
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,8 @@
# (4) resize pins with posy wrong if component has pins with D direction but not U direction
# (5) resize pins with posx wrong if component has at least one pin wrong in each of the following direction: L, R
# (6) resize pins with posy wrong if component has at least one pin wrong in each of the following direction: U, D
# (7) shifts pins with posx to 100mil grid if pin is in U or D direction
# (8) shifts pins with posy to 100mil grid if pin is in L or R direction

class CheckComponent(object):
def __init__(self, component):
Expand All @@ -33,11 +35,16 @@ def __init__(self, component):
self.need_fix_U = False
self.need_fix_D = False

if args.verbose:
print('\tConsidering component: %s' % component.name)

## check the prerequisites

# component has only one rectangle
# assuming it as the body of the component
if len(component.draw['rectangles']) != 1:
if args.verbose:
print('\t\tNumber of rectangles != 1')
return

# all pins L and R have the same size
Expand All @@ -47,6 +54,8 @@ def __init__(self, component):
if self.pinsR_count > 0:
lengths += [pin['length'] for pin in self.pinsR]
if lengths and lengths.count(lengths[0]) != len(lengths):
if args.verbose:
print('\t\tMore than one pin length encountered on left or right side')
return

# all pins U and D have the same size
Expand All @@ -56,16 +65,22 @@ def __init__(self, component):
if self.pinsD_count > 0:
lengths += [pin['length'] for pin in self.pinsD]
if lengths and lengths.count(lengths[0]) != len(lengths):
if args.verbose:
print('\t\tMore than one pin length encountered on top or bottom')
return

# pins length have to be multiple of 50mil
for pin in component.pins:
if (int(pin['length']) % 50) != 0:
if args.verbose:
print('\t\tPin lengths are not all multiples of 50mil')
return

# pins posx and posy have to be multiple of 50mil
for pin in component.pins:
if (int(pin['posx']) % 50) != 0 or (int(pin['posy']) % 50) != 0:
if args.verbose:
print('\t\tPin positions are not all multiples of 50mil')
return

# check if at least one pin is wrong in each direction
Expand Down Expand Up @@ -94,12 +109,13 @@ def __init__(self, component):
if (posy % 100) != 0:
self.need_fix_D = True
break

if args.verbose:
print('\t\tWill fix component')
self.prerequisites_ok = True

def print_header(self):
if not self.header_printed:
print('\tcomponent: %s' % component.name)
print('\tComponent: %s' % component.name)
self.header_printed = True

def resize_pin(self, pin, new_len, pos, new_pos):
Expand All @@ -110,104 +126,145 @@ def resize_pin(self, pin, new_len, pos, new_pos):
pin['length'] = str(new_len)
pin[pos] = str(new_pos)

def resize_component_pins(component):
component = CheckComponent(component)
def resize_all_pins(self):

# case (1)
if component.pinsL_count > 0 and component.pinsR_count == 0:
for pin in component.pinsL:
posx = int(pin['posx'])
length = int(pin['length'])
# case (1)
if self.pinsL_count > 0 and self.pinsR_count == 0:
for pin in self.pinsL:
posx = int(pin['posx'])
length = int(pin['length'])

if (posx % 100) != 0:
if length <= 100:
length += 50
posx += 50
elif length >= 150:
length -= 50
posx -= 50
if (posx % 100) != 0:
if length <= 100:
length += 50
posx += 50
elif length >= 150:
length -= 50
posx -= 50

component.resize_pin(pin, length, 'posx', posx)
self.resize_pin(pin, length, 'posx', posx)

# case (2)
if component.pinsR_count > 0 and component.pinsL_count == 0:
for pin in component.pinsR:
posx = int(pin['posx'])
length = int(pin['length'])
# case (2)
if self.pinsR_count > 0 and self.pinsL_count == 0:
for pin in self.pinsR:
posx = int(pin['posx'])
length = int(pin['length'])

if (posx % 100) != 0:
if length <= 100:
length += 50
posx -= 50
elif length >= 150:
length -= 50
posx += 50
if (posx % 100) != 0:
if length <= 100:
length += 50
posx -= 50
elif length >= 150:
length -= 50
posx += 50

component.resize_pin(pin, length, 'posx', posx)
self.resize_pin(pin, length, 'posx', posx)

# case (3)
if component.pinsU_count > 0 and component.pinsD_count == 0:
for pin in component.pinsU:
posy = int(pin['posy'])
length = int(pin['length'])
# case (3)
if self.pinsU_count > 0 and self.pinsD_count == 0:
for pin in self.pinsU:
posy = int(pin['posy'])
length = int(pin['length'])

if (posy % 100) != 0:
if length <= 100:
length += 50
posy -= 50
elif length >= 150:
length -= 50
posy += 50

self.resize_pin(pin, length, 'posy', posy)

# case (4)
if self.pinsD_count > 0 and self.pinsU_count == 0:
for pin in self.pinsD:
posy = int(pin['posy'])
length = int(pin['length'])

if (posy % 100) != 0:
if length <= 100:
length += 50
posy += 50
elif length >= 150:
length -= 50
posy -= 50

self.resize_pin(pin, length, 'posy', posy)

# case (5)
if self.need_fix_L and self.need_fix_R:
for pin in (self.pinsL + self.pinsR):
posx = int(pin['posx'])
length = int(pin['length'])

if (posy % 100) != 0:
if length <= 100:
length += 50
posy -= 50
posx += 50 if posx > 0 else -50
elif length >= 150:
length -= 50
posy += 50
posx += -50 if posx > 0 else 50

component.resize_pin(pin, length, 'posy', posy)
self.resize_pin(pin, length, 'posx', posx)

# case (4)
if component.pinsD_count > 0 and component.pinsU_count == 0:
for pin in component.pinsD:
posy = int(pin['posy'])
length = int(pin['length'])
# case (6)
if self.need_fix_U and self.need_fix_D:
for pin in (self.pinsU + self.pinsD):
posy = int(pin['posy'])
length = int(pin['length'])

if (posy % 100) != 0:
if length <= 100:
length += 50
posy += 50
posy += 50 if posy > 0 else -50
elif length >= 150:
length -= 50
posy -= 50

component.resize_pin(pin, length, 'posy', posy)

# case (5)
if component.need_fix_L and component.need_fix_R:
for pin in (component.pinsL + component.pinsR):
posx = int(pin['posx'])
length = int(pin['length'])

if length <= 100:
length += 50
posx += 50 if posx > 0 else -50
elif length >= 150:
length -= 50
posx += -50 if posx > 0 else 50

component.resize_pin(pin, length, 'posx', posx)
posy += -50 if posy > 0 else 50

self.resize_pin(pin, length, 'posy', posy)

return self.header_printed

#shifts a pin after ensuring that doing so doesn't cause an overlap
def shift_pin(self,pin, oldx, oldy, newx, newy):
self.print_header()
if((newx, newy) in self.pin_positions):
if args.verbose:
print("\t\tshifting pin causes overlap: %s (%s) from %i,%i to %i,%i'" % (pin['name'], pin['num'], oldx, oldy, newx, newy))
return False
if args.verbose:
print('\t\t[movex] pin from %i,%i to %i,%i: %s (%s)' %
(oldx, oldy, newx, newy, pin['name'], pin['num']))
pin['posx'] = str(newx)
pin['posy'] = str(newy)
self.pin_positions.append((int(pin['posx']), int(pin['posy'])))


def shift_all_pins(self):

self.pin_positions = []

#initialize list of pin positions with current list
#this is later used to prevent pin overlaps as a result of shifts
for pin in (self.pinsU + self.pinsD + self.pinsL + self.pinsR):
self.pin_positions.append((int(pin['posx']), int(pin['posy'])))

# case (7)
for pin in (self.pinsU + self.pinsD):
posx = int(pin['posx'])
posy = int(pin['posy'])
newposx = posx - (posx%100)
if (newposx != posx):
self.shift_pin(pin, posx, posy, newposx, posy)

#case (8)
for pin in (self.pinsL + self.pinsR):
posx = int(pin['posx'])
posy = int(pin['posy'])
newposy = posy - (posy%100)
if (newposy != posy):
self.shift_pin(pin, posx, posy, posx, newposy)
return self.header_printed

# case (6)
if component.need_fix_U and component.need_fix_D:
for pin in (component.pinsU + component.pinsD):
posy = int(pin['posy'])
length = int(pin['length'])

if length <= 100:
length += 50
posy += 50 if posy > 0 else -50
elif length >= 150:
length -= 50
posy += -50 if posy > 0 else 50

component.resize_pin(pin, length, 'posy', posy)

return component.header_printed


parser = argparse.ArgumentParser()
Expand All @@ -220,7 +277,11 @@ def resize_component_pins(component):
lib = SchLib(libfile)
print('library: %s' % libfile)
for component in lib.components:
component_printed = resize_component_pins(component)
componentCheck = CheckComponent(component)

component_printed = componentCheck.resize_all_pins()
component_printed = componentCheck.shift_all_pins() or component_printed

if not component_printed:
if args.verbose:
print('\tcomponent: %s......OK' % component.name)
Expand Down