diff --git a/index.rst b/index.rst index b0dda3e9..d861495c 100644 --- a/index.rst +++ b/index.rst @@ -11,9 +11,9 @@ Contents: .. toctree:: :maxdepth: 2 -.. automodule:: ipmi_command +.. automodule:: ipmi.command -.. autoclass:: ipmi_command +.. autoclass:: ipmi.command :members: Indices and tables diff --git a/ipmi/__init__.py b/ipmi/__init__.py new file mode 100644 index 00000000..e69de29b diff --git a/ipmi_command.py b/ipmi/command.py similarity index 98% rename from ipmi_command.py rename to ipmi/command.py index 09b76da6..7a20aaee 100644 --- a/ipmi_command.py +++ b/ipmi/command.py @@ -15,7 +15,7 @@ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the specific language governing permissions and limitations under the License. """ -from ipmi_session import ipmi_session, call_with_optional_args +from ipmi.session import Session, call_with_optional_args def _raiseorcall(callback,response,args=None): if callback is None: if 'error' in response: @@ -51,7 +51,7 @@ power_states = { "boot": -1, #not a valid direct boot state, but here for convenience of 'in' statement } -class ipmi_command(object): +class Command(object): """Send IPMI commands to BMCs. This object represents a persistent session to an IPMI device (bmc) and @@ -74,7 +74,7 @@ class ipmi_command(object): def __init__(self,bmc,userid,password,kg=None): #TODO(jbjohnso): accept tuples and lists of each parameter for mass #operations without pushing the async complexities up the stack - self.ipmi_session=ipmi_session(bmc=bmc, + self.ipmi_session=Session(bmc=bmc, userid=userid, password=password, kg=kg) @@ -104,7 +104,7 @@ class ipmi_command(object): self.requestpending=True if self.commandcallback is None: while self.requestpending: - ipmi_session.wait_for_rsp() + Session.wait_for_rsp() return self.lastresponse return True @@ -233,7 +233,7 @@ class ipmi_command(object): callback=self._bootdev_timer_disabled) if callback is None: while self.requestpending: - ipmi_session.wait_for_rsp() + Session.wait_for_rsp() return self.lastresponse def _bootdev_timer_disabled(self,response): diff --git a/ipmi_constants.py b/ipmi/constants.py similarity index 100% rename from ipmi_constants.py rename to ipmi/constants.py diff --git a/ipmi_session.py b/ipmi/session.py similarity index 97% rename from ipmi_session.py rename to ipmi/session.py index 8350d433..c812dcda 100644 --- a/ipmi_session.py +++ b/ipmi/session.py @@ -29,7 +29,7 @@ from time import time from Crypto.Cipher import AES from Crypto.Hash import HMAC, SHA -from ipmi_constants import payload_types, ipmi_completion_codes, command_completion_codes, payload_types, rmcp_codes +from ipmi.constants import payload_types, ipmi_completion_codes, command_completion_codes, payload_types, rmcp_codes initialtimeout = 0.5 #minimum timeout for first packet to retry in any given #session. This will be randomized to stagger out retries @@ -79,7 +79,7 @@ def get_ipmi_error(response,suffix=""): else: return "Unknown code "+code+" encountered" -class ipmi_session: +class Session: poller=select.poll() bmc_handlers={} waiting_sessions={} @@ -155,12 +155,12 @@ class ipmi_session: else: self.async=True self.onlogon=onlogon - if not hasattr(ipmi_session,'socket'): + if not hasattr(Session,'socket'): self._createsocket() self.login() if not self.async: while not self.logged: - ipmi_session.wait_for_rsp() + Session.wait_for_rsp() def _initsession(self): self.localsid=2017673555 #this number can be whatever we want. I picked #'xCAT' minus 1 so that a hexdump of packet @@ -248,7 +248,7 @@ class ipmi_session: self._send_ipmi_net_payload(netfn,command,data) if callback is None: while self.lastresponse is None: - ipmi_session.wait_for_rsp() + Session.wait_for_rsp() return self.lastresponse def _send_ipmi_net_payload(self,netfn,command,data): ipmipayload=self._make_ipmi_payload(netfn,command,data) @@ -778,7 +778,7 @@ class ipmi_session: self.expectedcmd=0x1ff self.seqlun += 4 #prepare seqlun for next transmit self.seqlun &= 0xff #when overflowing, wrap around - del ipmi_session.waiting_sessions[self] + del Session.waiting_sessions[self] self.lastpayload=None #render retry mechanism utterly incapable of doing #anything, though it shouldn't matter self.last_payload_type=None @@ -837,17 +837,17 @@ class ipmi_session: def _xmit_packet(self): if not self.nowait: #if we are retrying, we really need to get the #packet out and get our timeout updated - ipmi_session.wait_for_rsp(timeout=0) #take a convenient opportunity + Session.wait_for_rsp(timeout=0) #take a convenient opportunity #to drain the socket queue if #applicable - while ipmi_session.pending > ipmi_session.maxpending: - ipmi_session.wait_for_rsp() - ipmi_session.waiting_sessions[self]={} - ipmi_session.waiting_sessions[self]['ipmisession']=self - ipmi_session.waiting_sessions[self]['timeout']=self.timeout+time() - ipmi_session.pending+=1 + while Session.pending > Session.maxpending: + Session.wait_for_rsp() + Session.waiting_sessions[self]={} + Session.waiting_sessions[self]['ipmisession']=self + Session.waiting_sessions[self]['timeout']=self.timeout+time() + Session.pending+=1 if self.sockaddr: - ipmi_session.socket.sendto(self.netpacket,self.sockaddr) + Session.socket.sendto(self.netpacket,self.sockaddr) else: #he have not yet picked a working sockaddr for this connection, #try all the candidates that getaddrinfo provides for res in socket.getaddrinfo(self.bmc, @@ -858,8 +858,8 @@ class ipmi_session: if (res[0] == socket.AF_INET): #convert the sockaddr to AF_INET6 newhost='::ffff:'+sockaddr[0] sockaddr = (newhost,sockaddr[1],0,0) - ipmi_session.bmc_handlers[sockaddr]=self - ipmi_session.socket.sendto(self.netpacket,sockaddr) + Session.bmc_handlers[sockaddr]=self + Session.socket.sendto(self.netpacket,sockaddr) if self.sequencenumber: #seq number of zero will be left alone as it is #special, otherwise increment self.sequencenumber += 1 @@ -884,7 +884,7 @@ class ipmi_session: if __name__ == "__main__": import sys - ipmis = ipmi_session(bmc=sys.argv[1], + ipmis = Session(bmc=sys.argv[1], userid=sys.argv[2], password=os.environ['IPMIPASS']) print ipmis.raw_command(command=2,data=[1],netfn=0) diff --git a/ipmictl.py b/ipmictl.py index 46d2ec1f..cd08b00c 100755 --- a/ipmictl.py +++ b/ipmictl.py @@ -23,7 +23,7 @@ understand how the ipmi_command class workes. import os import sys -from ipmi_command import ipmi_command +from ipmi.command import Command password=os.environ['IPMIPASSWORD'] os.environ['IPMIPASSWORD']="" if (len(sys.argv) < 3): @@ -36,7 +36,7 @@ command=sys.argv[3] arg=None if len(sys.argv)==5: arg=sys.argv[4] -ipmicmd = ipmi_command(bmc=bmc,userid=userid,password=password) +ipmicmd = Command(bmc=bmc,userid=userid,password=password) if command == 'power': if arg: print ipmicmd.set_power(arg,wait=True) diff --git a/setup.py b/setup.py new file mode 100644 index 00000000..33f33b93 --- /dev/null +++ b/setup.py @@ -0,0 +1,12 @@ +#!/usr/bin/env python + +from distutils.core import setup + +setup(name='python-ipmi', + version='0.1', + description='Python IPMI implementation', + author='Jarrod Johnson', + author_email='jbjohnso@us.ibm.com', + url='http://xcat.sf.net/', + packages=['ipmi'], + )