1 /* 2 * Copyright 2009, Ingo Weinhold, ingo_weinhold@gmx.de. 3 * Copyright 2011, Oliver Tappe <zooey@hirschkaefer.de> 4 * Distributed under the terms of the MIT License. 5 */ 6 7 8 #include "package.h" 9 10 #include <errno.h> 11 #include <getopt.h> 12 #include <stdio.h> 13 #include <stdlib.h> 14 #include <string.h> 15 16 #include <package/hpkg/HPKGDefs.h> 17 18 19 extern const char* __progname; 20 const char* kCommandName = __progname; 21 22 23 static const char* kUsage = 24 "Usage: %s <command> <command args>\n" 25 "Creates, inspects, or extracts a Haiku package.\n" 26 "\n" 27 "Commands:\n" 28 " add [ <options> ] <package> <entries>...\n" 29 " Adds the specified entries <entries> to package file <package>.\n" 30 "\n" 31 " -0 ... -9 - Use compression level 0 ... 9. 0 means no, 9 best\n" 32 " compression. Defaults to 9.\n" 33 " -C <dir> - Change to directory <dir> before adding entries.\n" 34 " -f - Force adding, replacing already existing entries. Without\n" 35 " this option adding will fail when encountering a\n" 36 " pre-existing entry (directories will be merged, though).\n" 37 " -i <info> - Use the package info file <info>. It will be added as\n" 38 " \".PackageInfo\", overriding a \".PackageInfo\" file,\n" 39 " existing.\n" 40 " -q - Be quiet (don't show any output except for errors).\n" 41 " -v - Be verbose (show more info about created package).\n" 42 "\n" 43 " checksum [ <options> ] [ <package> ]\n" 44 " Computes the checksum of package file <package>. If <package> is omitted\n" 45 " or \"-\", the file is read from stdin. This is only supported, if the\n" 46 " package is uncompressed.\n" 47 "\n" 48 " -q - Be quiet (don't show any output except for errors).\n" 49 " -v - Be verbose (show more info about created package).\n" 50 "\n" 51 " create [ <options> ] <package>\n" 52 " Creates package file <package> from contents of current directory.\n" 53 "\n" 54 " -0 ... -9 - Use compression level 0 ... 9. 0 means no, 9 best\n" 55 " compression. Defaults to 9.\n" 56 " -b - Create an empty build package. Only the .PackageInfo will\n" 57 " be added.\n" 58 " -C <dir> - Change to directory <dir> before adding entries.\n" 59 " -i <info> - Use the package info file <info>. It will be added as\n" 60 " \".PackageInfo\", overriding a \".PackageInfo\" file,\n" 61 " existing.\n" 62 " -I <path> - Set the package's installation path to <path>. This is\n" 63 " an option only for use in package building. It will cause\n" 64 " the package .self link to point to <path>, which is useful\n" 65 " to redirect a \"make install\". Only allowed with -b.\n" 66 " -z <type> - Specify compression method to use.\n" 67 " -q - Be quiet (don't show any output except for errors).\n" 68 " -v - Be verbose (show more info about created package).\n" 69 "\n" 70 " dump [ <options> ] <package>\n" 71 " Dumps the TOC section of package file <package>. For debugging only.\n" 72 "\n" 73 " extract [ <options> ] <package> [ <entries>... ]\n" 74 " Extracts the contents of package file <package>. If <entries> are\n" 75 " specified, only those entries are extracted (directories recursively).\n" 76 "\n" 77 " -C <dir> - Change to directory <dir> before extracting the contents\n" 78 " of the archive.\n" 79 " -i <info> - Extract the .PackageInfo file to <info> instead.\n" 80 "\n" 81 " info [ <options> ] <package>\n" 82 " Prints individual meta information of package file <package>.\n" 83 "\n" 84 " -f <format>, --format <format>\n" 85 " - Print the given format string, performing the following\n" 86 " replacements:\n" 87 " %%fileName%% - the package's canonical file name\n" 88 " %%name%% - the package name\n" 89 " %%version%% - the package version\n" 90 " %%%% - %%\n" 91 " \\n - new line\n" 92 " \\t - tab\n" 93 "\n" 94 " list [ <options> ] <package>\n" 95 " Lists the contents of package file <package>.\n" 96 "\n" 97 " -a - Also list the file attributes.\n" 98 " -i - Only print the meta information, not the files.\n" 99 " -p - Only print a list of file paths.\n" 100 "\n" 101 " recompress [ <options> ] <input package> <output package>\n" 102 " Reads the package file <input package> and writes it to new package\n" 103 " <output package> using the specified compression options. If the\n" 104 " compression level 0 is specified (i.e. no compression), " 105 "<output package>\n" 106 " can be \"-\", in which case the data are written to stdout.\n" 107 " If the input files doesn't use compression <input package>\n" 108 " can be \"-\", in which case the data are read from stdin.\n" 109 "\n" 110 " -0 ... -9 - Use compression level 0 ... 9. 0 means no, 9 best\n" 111 " compression. Defaults to 9.\n" 112 " -z <type> - Specify compression method to use.\n" 113 " -q - Be quiet (don't show any output except for errors).\n" 114 " -v - Be verbose (show more info about created package).\n" 115 "\n" 116 "Common Options:\n" 117 " -h, --help - Print this usage info.\n" 118 ; 119 120 121 void 122 print_usage_and_exit(bool error) 123 { 124 fprintf(error ? stderr : stdout, kUsage, kCommandName); 125 exit(error ? 1 : 0); 126 } 127 128 129 int32 130 parse_compression_argument(const char* arg) 131 { 132 if (arg == NULL) { 133 // Default compression method. 134 #ifdef ZSTD_DEFAULT 135 return BPackageKit::BHPKG::B_HPKG_COMPRESSION_ZSTD; 136 #else 137 return BPackageKit::BHPKG::B_HPKG_COMPRESSION_ZLIB; 138 #endif 139 } 140 141 if (strcmp(arg, "zstd") == 0) { 142 return BPackageKit::BHPKG::B_HPKG_COMPRESSION_ZSTD; 143 } else if (strcmp(arg, "zlib") == 0) { 144 return BPackageKit::BHPKG::B_HPKG_COMPRESSION_ZLIB; 145 } else { 146 fprintf(stderr, "error: unknown compression method '%s'\n", arg); 147 exit(1); 148 } 149 } 150 151 152 int 153 main(int argc, const char* const* argv) 154 { 155 if (argc < 2) 156 print_usage_and_exit(true); 157 158 const char* command = argv[1]; 159 if (strcmp(command, "add") == 0) 160 return command_add(argc - 1, argv + 1); 161 162 if (strcmp(command, "checksum") == 0) 163 return command_checksum(argc - 1, argv + 1); 164 165 if (strcmp(command, "create") == 0) 166 return command_create(argc - 1, argv + 1); 167 168 if (strcmp(command, "dump") == 0) 169 return command_dump(argc - 1, argv + 1); 170 171 if (strcmp(command, "extract") == 0) 172 return command_extract(argc - 1, argv + 1); 173 174 if (strcmp(command, "list") == 0) 175 return command_list(argc - 1, argv + 1); 176 177 if (strcmp(command, "info") == 0) 178 return command_info(argc - 1, argv + 1); 179 180 if (strcmp(command, "recompress") == 0) 181 return command_recompress(argc - 1, argv + 1); 182 183 if (strcmp(command, "help") == 0) 184 print_usage_and_exit(false); 185 else 186 print_usage_and_exit(true); 187 188 // never gets here 189 return 0; 190 } 191