summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--include/slibtool/slibtool.h3
-rw-r--r--src/internal/slibtool_ar_impl.h1
-rw-r--r--src/logic/slbt_exec_ar.c42
-rw-r--r--src/skin/slbt_skin_ar.c7
4 files changed, 53 insertions, 0 deletions
diff --git a/include/slibtool/slibtool.h b/include/slibtool/slibtool.h
index 1eac876..5095ebb 100644
--- a/include/slibtool/slibtool.h
+++ b/include/slibtool/slibtool.h
@@ -73,6 +73,7 @@ extern "C" {
#define SLBT_DRIVER_OUTPUT_MACHINE SLBT_DRIVER_XFLAG(0x1000)
#define SLBT_DRIVER_MODE_AR SLBT_DRIVER_XFLAG(0x010000)
+#define SLBT_DRIVER_MODE_AR_CHECK SLBT_DRIVER_XFLAG(0x020000)
/* unit action flags */
#define SLBT_ACTION_MAP_READWRITE 0x0001
@@ -107,6 +108,8 @@ enum slbt_custom_error {
SLBT_ERR_AR_DUPLICATE_LONG_NAMES,
SLBT_ERR_AR_DUPLICATE_ARMAP_MEMBER,
SLBT_ERR_AR_MISPLACED_ARMAP_MEMBER,
+ SLBT_ERR_AR_NO_ACTION_SPECIFIED,
+ SLBT_ERR_AR_NO_INPUT_SPECIFIED,
};
/* execution modes */
diff --git a/src/internal/slibtool_ar_impl.h b/src/internal/slibtool_ar_impl.h
index 13cd6ef..9287832 100644
--- a/src/internal/slibtool_ar_impl.h
+++ b/src/internal/slibtool_ar_impl.h
@@ -9,6 +9,7 @@ extern const struct argv_option slbt_ar_options[];
enum ar_tags {
TAG_AR_HELP,
+ TAG_AR_CHECK,
};
struct ar_armaps_impl {
diff --git a/src/logic/slbt_exec_ar.c b/src/logic/slbt_exec_ar.c
index 56eee4e..3e1c0f2 100644
--- a/src/logic/slbt_exec_ar.c
+++ b/src/logic/slbt_exec_ar.c
@@ -12,6 +12,8 @@
#include "slibtool_errinfo_impl.h"
#include "argv/argv.h"
+#define SLBT_DRIVER_MODE_AR_ACTIONS (SLBT_DRIVER_MODE_AR_CHECK)
+
static int slbt_ar_usage(
int fdout,
const char * program,
@@ -68,8 +70,11 @@ int slbt_exec_ar(
{
int ret;
int fdout;
+ int fderr;
char ** argv;
char ** iargv;
+ struct slbt_driver_ctx_impl * ictx;
+ const struct slbt_common_ctx * cctx;
struct slbt_archive_ctx ** arctxv;
struct slbt_archive_ctx ** arctxp;
const char ** unitv;
@@ -91,8 +96,13 @@ int slbt_exec_ar(
/* initial state, ar mode skin */
slbt_reset_arguments(ectx);
slbt_disable_placeholders(ectx);
+
+ ictx = slbt_get_driver_ictx(dctx);
+ cctx = dctx->cctx;
iargv = ectx->cargv;
+
fdout = slbt_driver_fdout(dctx);
+ fderr = slbt_driver_fderr(dctx);
/* missing arguments? */
argv_optv_init(slbt_ar_options,optv);
@@ -131,6 +141,10 @@ int slbt_exec_ar(
dctx->cctx->drvflags
& SLBT_DRIVER_ANNOTATE_NEVER);
return 0;
+
+ case TAG_AR_CHECK:
+ ictx->cctx.drvflags |= SLBT_DRIVER_MODE_AR_CHECK;
+ break;
}
if (entry->fval) {
@@ -141,6 +155,34 @@ int slbt_exec_ar(
};
}
+ /* at least one action must be specified */
+ if (!(cctx->drvflags & SLBT_DRIVER_MODE_AR_ACTIONS)) {
+ if (cctx->drvflags & SLBT_DRIVER_VERBOSITY_ERRORS)
+ slbt_dprintf(fderr,
+ "%s: at least one action must be specified\n",
+ dctx->program);
+
+ return slbt_exec_ar_fail(
+ actx,meta,
+ SLBT_CUSTOM_ERROR(
+ dctx,
+ SLBT_ERR_AR_NO_ACTION_SPECIFIED));
+ }
+
+ /* at least one unit must be specified */
+ if (!nunits) {
+ if (cctx->drvflags & SLBT_DRIVER_VERBOSITY_ERRORS)
+ slbt_dprintf(fderr,
+ "%s: all actions require at least one input unit\n",
+ dctx->program);
+
+ return slbt_exec_ar_fail(
+ actx,meta,
+ SLBT_CUSTOM_ERROR(
+ dctx,
+ SLBT_ERR_AR_NO_INPUT_SPECIFIED));
+ }
+
/* archive vector allocation */
if (!(arctxv = calloc(nunits+1,sizeof(struct slbt_archive_ctx *))))
return slbt_exec_ar_fail(
diff --git a/src/skin/slbt_skin_ar.c b/src/skin/slbt_skin_ar.c
index 4376421..4ef38d7 100644
--- a/src/skin/slbt_skin_ar.c
+++ b/src/skin/slbt_skin_ar.c
@@ -5,5 +5,12 @@ const struct argv_option slbt_ar_options[] = {
{"help", 'h',TAG_AR_HELP,ARGV_OPTARG_NONE,0,0,0,
"display ar mode help"},
+ {"Wcheck", 0,TAG_AR_CHECK,ARGV_OPTARG_NONE,
+ ARGV_OPTION_HYBRID_ONLY,
+ "[ARCHIVE-FILE]",0,
+ "verify that %s is a valid archive; "
+ "supported variants are BSD, SysV, and PE/COFF"},
+
+
{0,0,0,0,0,0,0,0}
};