предварительный вариант парсера готов, прошу критики, за профили пока не брался
<code>
#!/usr/bin/python
# coding: utf-8
'''Читает из /proc/cmdline параметры определяющие настройку сети, а также задающие public ключи для sshd
dsapub=<DSA-PUBLIC-KEY> rsapub=<RSA-PUBLIC-KEY> заносит их в /root/.ssh/authorized_keys
rename_<MAC>=<ETH_NAME> переименоввывает интерфейс с заданным MAC-address в <ETH_NAME>, сдесь и далее <MAC>==([0-9a-f]{12,12})
(чтоб небыло путаницы когда несколько интерфейсов) пока что недоделал
routes_<ETH_NAME>=(deafult|<NET_ADDRESS>):<IP_ADDRESS> (deafult|<NET_ADDRESS>) via <IP_ADDRESS>
config_<ETH_NAME>=IP.AD.DR.ES/NETMASK|null|noop|dhcp
mac_<ETH_NAME>=<MAC>'''
from re import match
from os.path import dirname
from os import makedirs, chmod, symlink
from subprocess import Popen
AK_PATH='/root/.ssh/authorized_keys'
NET_PATH='/etc/conf.d/net'
CMDLINE='/proc/cmdline'
## это на время проверки
AK_PATH='/tmp/root/.ssh/authorized_keys'
NET_PATH='/tmp/net'
CMDLINE='./cmdline'
params=[ p.split('=',1) for p in open(CMDLINE).readline().split()]
def get_keys():
'''Возвращает список строк готовых для записи в authorized_keys'''
return ['dsapub'==p[0] and 'ssh-dss %s root@localhost\n'%p[1] or 'ssh-rsa %s root@localhost\n'%p[1]
for p in params if 2==len(p) and p[0] in ['dsapub','rsapub']]
def dossh():
'''Если список возвращаемый get_keys() не пуст - пишет его и добавляет sshd в default '''
authorized_keys=get_keys()
if not authorized_keys: return
try: makedirs(dirname(AK_PATH),0o700)
except: pass
try:
open(AK_PATH,'a').writelines(authorized_keys)
chmod(AK_PATH,0o600)
except: pass
Popen('/sbin/rc-update add sshd default', shell=True)
def get_net_setups():
confnet={}
P={ '32':'([12]?\d|3[0-2])',
'mac':'([0-9a-fA-F]){12,12}',
'ip':'(1?\d{1,2}|2[0-4]\d|25[0-5])\.(1?\d{1,2}|2[0-4]\d|25[0-5])\.(1?\d{1,2}|2[0-4]\d|25[0-5])\.(1?\d{1,2}|2[0-4]\d|25[0-5])',
}## patterns
for p in params:
if match('routes_eth\d',p[0]) and match('^(default|%(ip)s/%(32)s):%(ip)s$'%P, p[1]):
confnet[p[0]]=confnet.pop(p[0],' ') + ' %s via %s\n'%tuple(p[1].split(':'))
elif match('config_eth\d', p[0]) and match('^(%(ip)s(/%(32)s)?|null|noop|dhcp)$'%P, p[1]):
confnet[p[0]]=confnet.pop(p[0],' ')+p[1]+' '
elif match('mac_eth\d', p[0]) and match('^(%(mac)s)$'%P, p[1]):
confnet[p[0]]=p[1]
return confnet
def donet():
'''Настривает /etc/conf.d/net и добавляет в default использованные интерфейсы'''
try: open(NET_PATH,'a').writelines(['%s="%s"\n'%(p[0],p[1].strip()) for p in get_net_setups().items()])
except: pass
for h in reduce(lambda rslt,x: x not in rslt and rslt+[x] or rslt, [x.split('_',1)[1] for x in list(get_net_setups())], []):
try:
symlink('net.lo','/etc/init.d/net.%s'%h)
Popen('/sbin/rc-update add net.%s default'%h, shell=True)
except: pass
</code>
при тестировании использовал следующий файл
<code># cat ./cmdline
root=/dev/sda7 vga=791 resume=/dev/sda5 init=/sbin/bootchartd dsapub=AAAAB3NzaC1kc3MAAACBAJQVT8eez5PBUb8zN3NRg1V3SLJtnNQKkhfWpwZzs3aW6qN1t1okYY7xeoYNzBRt/pRXM2F44dSbSAjZTg1hvhgJxamsn4X3pQ/1rQED+GOxI10pK9vQVs3KmRGWTI8KODsgNuHt3DtOb48KhxLkDg+gnEGihHcNxcsZcEhFnxIfAAAAFQDwzclkU+UitdjLds3/5FItiyhx6wAAAIBE/83WwJzQrTKwGGjKg4eppPU9hplOHQvCp6dLFpf9UybW/fXAiMHMg4awnSyer6weuYCNYGtUFElpMFxwAQVghMamC9A+AQ5ff7var1bHKuqjoH1a7RZRx9HojIe7U+dvU4phk/3wSYDbBH5J2gISnj9DshcFlR5z1A9mIWagMQAAAIEAhf7VbEgbUUO0peCk3Ndt7TxbZlyGZqkBE7W//5XUuz9//Z4GtXZufDGm2DyrcIiSSw6rAYSPDSO8W6U4YxxwE4/EvCTkSEVpJgK0ocEdrfyscuMio/IEnljZ9s526SgBl5//0ctaGmcPnqNIY7EzcI3bp6g1/9qE3hv1P3aoYS0= rsapub=AAAAB3NzaC1yc2EAAAABIwAAAQEArlnMPGG3+fCDO4ctoy+VtxKPHB5XBFY/CP8KYIUC2ih3vD60AYOacmQiE440gRD1GV5FrEBrxfHBhXmn22ss11iw6VZ1i7cThNvgoystQfBf9owVJFvdE30pxA5NL6+apf/iOd5enI5Usmqc8tjNQISNJxhk/OeVTVdY7H+6YSdGw81K+tGRGSGa2Wh3ayRzcBb82Vl8q56Ipu848mhe15EfyrmIIre6CFEn+CqjzKLY5IbapXyxPiXoB5jArAnk3e0Brlgbas0wRDmvq3kE1615YYRBICyCMQBd/HeFPEZyiLWlPoSUp2Pbt4pIahk5HPKjomUjX2QnVoSF9YIuTw== mac_eth0=112233445566 config_eth0=192.168.2.3/24 config_eth0=10.11.12.13/8 routes_eth0=default:192.168.0.1 routes_eth0=172.16.0.0/16:10.10.10.1
</code>
соответственно параметры:
- dsapub=AAAAB… - dsa-public-key
- rsapub=AAAAB3N… - rsa-public-key
- mac_eth0=112233445566 - как и в /etc/conf.d/net - новый mac-аддрес (а вдруг надо)
- config_eth0=192.168.2.3/24 - как и в /etc/conf.d/net
- config_eth0=10.11.12.13/8 - второй IP, соответственно добавляется
- routes_eth0=default:192.168.0.1 - как и выше
- routes_eth0=172.16.0.0/16:10.10.10.1 - как и выше
здесь в параметре routes что:через_кого разделяю знаком :
ничего умнее придумать не смог, поскольку и остальные подпараметры ядра разделяются этим знаком
в принципе можно былоб сюда еще привязать Bonding и кучу других параметров, но все это можно сделать и с запущенной системы, главное на неее попасть.
rename_=<ETH_NAME> задумал, чтоб можно было явно указать какой интерфейс как называть, имеет смысл если есть несколько интерфейсов и неясно какой ядро определит первым, править скриптом /etc/udev/rules.d/70-persistent-net.rules до запуска /etc/init.d/udev нехочу, ибо некошерно это.
если кто знает как/чем заставить udev переименовать интерфейс - буду благодарен за подсказку.
в принципе dsapub,rsapub по идее можно былоб и проверять на наличие этих ключей в authorized_keys, но я же предполагаю, что этот скрипт используется лишь в LiveCD, ибо он слишком опасен если grub незапоролен
приму советы настройку еще чего стоит включить, для обеспечения дистанционного доступа к системе через параметры ядра