text: #!/usr/bin/env python
  #
  # rfkill control code
  #
  # Copyright (c) 2015	Intel Corporation
  #
  # Author: Johannes Berg <johannes.berg@intel.com>
  #
  # This software may be distributed under the terms of the MIT license.
  # See COPYING for more details.
  
  import struct
  import fcntl
  import os
  
  (TYPE_ALL,
   TYPE_WLAN,
   TYPE_BLUETOOTH,
   TYPE_UWB,
   TYPE_WIMAX,
   TYPE_WWAN,
   TYPE_GPS,
   TYPE_FM,
   TYPE_NFC) = range(9)
  
  (_OP_ADD,
   _OP_DEL,
   _OP_CHANGE,
   _OP_CHANGE_ALL) = range(4)
  
  _type_names = {
      TYPE_ALL: "all",
      TYPE_WLAN: "Wireless LAN",
      TYPE_BLUETOOTH: "Bluetooth",
      TYPE_UWB: "Ultra-Wideband",
      TYPE_WIMAX: "WiMAX",
      TYPE_WWAN: "Wireless WAN",
      TYPE_GPS: "GPS",
      TYPE_FM: "FM",
      TYPE_NFC: "NFC",
  }
  
  # idx, type, op, soft, hard
  _event_struct = '@IBBBB'
  _event_sz = struct.calcsize(_event_struct)
  
  class RFKillException(Exception):
      pass
  
  class RFKill(object):
      def __init__(self, idx):
          self._idx = idx
          self._type = None
  
      @property
      def idx(self):
          return self._idx
  
      @property
      def name(self):
          return open('/sys/class/rfkill/rfkill%d/name' % self._idx, 'r').read().rstrip()
  
      @property
      def type(self):
          if not self._type:
              for r, s, h in RFKill.list():
                  if r.idx == self.idx:
                      self._type = r._type
                      break
          return self._type
  
      @property
      def type_name(self):
          return _type_names.get(self._type, "unknown")
  
      @property
      def blocked(self):
          l = RFKill.list()
          for r, s, h in l:
              if r.idx == self.idx:
                  return (s, h)
          raise RFKillException("RFKill instance no longer exists")
  
      @property
      def soft_blocked(self):
          return self.blocked[0]
          
      @soft_blocked.setter
      def soft_blocked(self, block):
          if block:
              self.block()
          else:
              self.unblock()
  
      @property
      def hard_blocked(self):
          return self.blocked[1]
  
      def block(self):
          rfk = open('/dev/rfkill', 'w')
          s = struct.pack(_event_struct, self.idx, TYPE_ALL, _OP_CHANGE, 1, 0)
          rfk.write(s)
          rfk.close()
  
      def unblock(self):
          rfk = open('/dev/rfkill', 'w')
          s = struct.pack(_event_struct, self.idx, TYPE_ALL, _OP_CHANGE, 0, 0)
          rfk.write(s)
          rfk.close()
  
      @classmethod
      def block_all(cls, t=TYPE_ALL):
          rfk = open('/dev/rfkill', 'w')
          print rfk
          s = struct.pack(_event_struct, 0, t, _OP_CHANGE_ALL, 1, 0)
          rfk.write(s)
          rfk.close()
  
      @classmethod
      def unblock_all(cls, t=TYPE_ALL):
          rfk = open('/dev/rfkill', 'w')
          s = struct.pack(_event_struct, 0, t, _OP_CHANGE_ALL, 0, 0)
          rfk.write(s)
          rfk.close()
  
      @classmethod
      def list(cls):
          res = []
          rfk = open('/dev/rfkill', 'r')
          fd = rfk.fileno()
          flgs = fcntl.fcntl(fd, fcntl.F_GETFL)
          fcntl.fcntl(fd, fcntl.F_SETFL, flgs | os.O_NONBLOCK)
          while True:
              try:
                  d = rfk.read(_event_sz)
                  _idx, _t, _op, _s, _h = struct.unpack(_event_struct, d)
                  if _op != _OP_ADD:
                      continue
                  r = RFKill(_idx)
                  r._type = _t
                  res.append((r, _s, _h))
              except IOError:
                  break
          return res
  
  if __name__ == "__main__":
      for r, s, h in RFKill.list():
          print "%d: %s: %s" % (r.idx, r.name, r.type_name)
          print "\tSoft blocked: %s" % ("yes" if s else "no")
          print "\tHard blocked: %s" % ("yes" if h else "no")
  