3 # Copyright (c) 2011 Intel, Inc.
5 # This program is free software; you can redistribute it and/or modify it
6 # under the terms of the GNU General Public License as published by the Free
7 # Software Foundation; version 2 of the License
9 # This program is distributed in the hope that it will be useful, but
10 # WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
11 # or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
14 # You should have received a copy of the GNU General Public License along
15 # with this program; if not, write to the Free Software Foundation, Inc., 59
16 # Temple Place - Suite 330, Boston, MA 02111-1307, USA.
19 from mic import msger, creator, __version__ as VERSION
20 from mic.utils import cmdln, misc, errors
21 from mic.conf import configmgr
22 from mic.plugin import pluginmgr
25 def optparser_setup(func):
26 """Setup optparser for a function"""
27 if not hasattr(func, "optparser"):
28 func.optparser = cmdln.SubCmdOptionParser()
29 func.optparser.disable_interspersed_args()
33 class MicCmd(cmdln.Cmdln):
35 Usage: mic SUBCOMMAND [OPTS] [ARGS...]
37 mic Means the Image Creation tool
38 Try 'mic help SUBCOMMAND' for help on a specific subcommand.
48 def print_version(self):
49 msger.raw("%s %s (%s)" % (self.name,
51 misc.get_distro_str()))
53 def get_optparser(self):
54 optparser = cmdln.CmdlnOptionParser(self, version=self.version)
55 # hook optparse print_version here
56 optparser.print_version = self.print_version
57 optparser.add_option('-d', '--debug', action='store_true',
59 help='print debug message')
60 optparser.add_option('-v', '--verbose', action='store_true',
62 help='verbose information')
65 def postoptparse(self):
66 if self.options.verbose:
67 msger.set_loglevel('VERBOSE')
69 if self.options.debug:
72 rpm.setVerbosity(rpm.RPMLOG_NOTICE)
76 msger.set_loglevel('DEBUG')
80 def help_create(self):
81 crobj = creator.Creator()
82 crobj.optparser = crobj.get_optparser()
84 doc = crobj._help_reindent(doc)
85 doc = crobj._help_preprocess(doc, None)
86 doc = doc.replace(crobj.name, "${cmd_name}", 1)
87 doc = doc.rstrip() + '\n'
91 def do_create(self, argv):
92 crobj = creator.Creator()
95 def _root_confirm(self):
97 msger.error('Root permission is required to continue, abort')
100 @cmdln.option("-S", "--shell",
101 action="store_true", dest="shell", default=False,
102 help="Launch shell before packaging the converted image")
103 def do_convert(self, subcmd, opts, *args):
104 """${cmd_name}: convert image format
107 mic convert <imagefile> <destformat>
114 handler = self._get_cmd_handler('convert')
115 if hasattr(handler, "optparser"):
116 handler.optparser.print_help()
120 raise errors.Usage("It need 2 arguments (1 given)")
122 (srcimg, destformat) = args
124 raise errors.Usage("Extra argument given")
126 if not os.path.exists(srcimg):
127 raise errors.CreatorError("Cannot find the image: %s" % srcimg)
131 configmgr.convert['shell'] = opts.shell
133 srcformat = misc.get_image_type(srcimg)
134 if srcformat == "ext3fsimg":
139 for iname, icls in pluginmgr.get_plugins('imager').iteritems():
140 if iname == srcformat and hasattr(icls, "do_unpack"):
142 if iname == destformat and hasattr(icls, "do_pack"):
145 if (srcimager and destimager) is None:
146 raise errors.CreatorError("Can't convert from %s to %s" \
147 % (srcformat, destformat))
156 if destformat in maptab:
157 imgname = os.path.splitext(os.path.basename(srcimg))[0]
158 dstname = "{0}.{1}".format(imgname, maptab[destformat])
160 if os.path.exists(dstname):
161 if msger.ask("Converted image %s seems existed, "
162 "remove and continue?" % dstname):
165 raise errors.Abort("Canceled")
167 base_on = srcimager.do_unpack(srcimg)
168 destimager.do_pack(base_on)
171 @cmdln.option('-s', '--saveto',
172 action='store', dest='saveto', default=None,
173 help="Save the unpacked image to specified dir")
175 def do_chroot(self, subcmd, opts, *args):
176 """${cmd_name}: chroot into an image
179 mic chroot [options] <imagefile> [command [arg]...]
186 handler = self._get_cmd_handler('chroot')
187 if hasattr(handler, "optparser"):
188 handler.optparser.print_help()
191 targetimage = args[0]
193 if not os.path.exists(targetimage):
194 raise errors.CreatorError("Cannot find the image: %s"
199 configmgr.chroot['saveto'] = opts.saveto
201 imagetype = misc.get_image_type(targetimage)
202 if imagetype in ("ext3fsimg", "ext4fsimg", "btrfsimg"):
206 for pname, pcls in pluginmgr.get_plugins('imager').iteritems():
207 if pname == imagetype and hasattr(pcls, "do_chroot"):
212 raise errors.CreatorError("Cannot support image type: %s" \
215 chrootclass.do_chroot(targetimage, args[1:])
217 if __name__ == "__main__":
222 except KeyboardInterrupt:
223 msger.error('\n^C catched, program aborted.')
225 # catch 'no space left' exception, etc
226 except IOError, ioerr:
227 if ioerr.errno == errno.ENOSPC:
228 msger.error('\nNo space left on device')
231 except errors.Usage, usage:
232 msger.error(str(usage))
234 except errors.Abort, msg:
237 except errors.CreatorError, err:
238 if msger.get_loglevel() == 'DEBUG':
240 msger.error(traceback.format_exc())
242 msger.error(str(err))