--- a/iptables/ip6tables-restore.c
+++ b/iptables/ip6tables-restore.c
@@ -14,6 +14,8 @@
 #include <string.h>
 #include <stdio.h>
 #include <stdlib.h>
+#include <stdarg.h>
+#include <setjmp.h>
 #include "ip6tables.h"
 #include "xtables.h"
 #include "libiptc/libip6tc.h"
@@ -25,6 +27,7 @@
 #define DEBUGP(x, args...)
 #endif
 
+static jmp_buf jmp;
 static int binary = 0, counters = 0, verbose = 0, noflush = 0;
 
 /* Keeping track of external matches and targets.  */
@@ -35,6 +38,7 @@ static const struct option options[] = {
 	{.name = "test",     .has_arg = false, .val = 't'},
 	{.name = "help",     .has_arg = false, .val = 'h'},
 	{.name = "noflush",  .has_arg = false, .val = 'n'},
+	{.name = "lenient",  .has_arg = false, .val = 'l'},
 	{.name = "modprobe", .has_arg = true,  .val = 'M'},
 	{.name = "table",    .has_arg = true,  .val = 'T'},
 	{NULL},
@@ -51,6 +55,7 @@ static void print_usage(const char *name
 			"	   [ --test ]\n"
 			"	   [ --help ]\n"
 			"	   [ --noflush ]\n"
+			"	   [ --lenient ]\n"
 			"          [ --modprobe=<command>]\n", name);
 
 	exit(1);
@@ -114,6 +119,17 @@ static void free_argv(void) {
 		free(newargv[i]);
 }
 
+static void catch_exit_error(enum xtables_exittype status, const char *msg, ...)
+{
+	va_list args;
+	fprintf(stderr, "line %d: ", line);
+	va_start(args, msg);
+	vfprintf(stderr, msg, args);
+	va_end(args);
+	fprintf(stderr, "\n");
+	longjmp(jmp, status);
+}
+
 static void add_param_to_argv(char *parsestart)
 {
 	int quote_open = 0, escaped = 0, param_len = 0;
@@ -204,7 +220,7 @@ int ip6tables_restore_main(int argc, cha
 	init_extensions6();
 #endif
 
-	while ((c = getopt_long(argc, argv, "bcvthnM:T:", options, NULL)) != -1) {
+	while ((c = getopt_long(argc, argv, "bcvthnlM:T:", options, NULL)) != -1) {
 		switch (c) {
 			case 'b':
 				binary = 1;
@@ -225,6 +241,9 @@ int ip6tables_restore_main(int argc, cha
 			case 'n':
 				noflush = 1;
 				break;
+			case 'l':
+				ip6tables_globals.exit_err = catch_exit_error;
+				break;
 			case 'M':
 				xtables_modprobe_program = optarg;
 				break;
@@ -437,8 +456,11 @@ int ip6tables_restore_main(int argc, cha
 			for (a = 0; a < newargc; a++)
 				DEBUGP("argv[%u]: %s\n", a, newargv[a]);
 
-			ret = do_command6(newargc, newargv,
-					 &newargv[2], &handle, true);
+			if (!setjmp(jmp))
+				ret = do_command6(newargc, newargv,
+						 &newargv[2], &handle, true);
+			else
+				ret = 1;
 
 			free_argv();
 			fflush(stdout);
--- a/iptables/iptables-restore.c
+++ b/iptables/iptables-restore.c
@@ -11,6 +11,8 @@
 #include <string.h>
 #include <stdio.h>
 #include <stdlib.h>
+#include <stdarg.h>
+#include <setjmp.h>
 #include "iptables.h"
 #include "xtables.h"
 #include "libiptc/libiptc.h"
@@ -22,6 +24,7 @@
 #define DEBUGP(x, args...)
 #endif
 
+static jmp_buf jmp;
 static int binary = 0, counters = 0, verbose = 0, noflush = 0;
 
 /* Keeping track of external matches and targets.  */
@@ -32,6 +35,7 @@ static const struct option options[] = {
 	{.name = "test",     .has_arg = false, .val = 't'},
 	{.name = "help",     .has_arg = false, .val = 'h'},
 	{.name = "noflush",  .has_arg = false, .val = 'n'},
+	{.name = "lenient",  .has_arg = false, .val = 'l'},
 	{.name = "modprobe", .has_arg = true,  .val = 'M'},
 	{.name = "table",    .has_arg = true,  .val = 'T'},
 	{NULL},
@@ -50,6 +54,7 @@ static void print_usage(const char *name
 			"	   [ --test ]\n"
 			"	   [ --help ]\n"
 			"	   [ --noflush ]\n"
+			"	   [ --lenient ]\n"
 			"	   [ --table=<TABLE> ]\n"
 			"          [ --modprobe=<command>]\n", name);
 
@@ -113,6 +118,17 @@ static void free_argv(void) {
 		free(newargv[i]);
 }
 
+static void catch_exit_error(enum xtables_exittype status, const char *msg, ...)
+{
+	va_list args;
+	fprintf(stderr, "line %d: ", line);
+	va_start(args, msg);
+	vfprintf(stderr, msg, args);
+	va_end(args);
+	fprintf(stderr, "\n");
+	longjmp(jmp, status);
+}
+
 static void add_param_to_argv(char *parsestart)
 {
 	int quote_open = 0, escaped = 0, param_len = 0;
@@ -204,7 +220,7 @@ iptables_restore_main(int argc, char *ar
 	init_extensions4();
 #endif
 
-	while ((c = getopt_long(argc, argv, "bcvthnM:T:", options, NULL)) != -1) {
+	while ((c = getopt_long(argc, argv, "bcvthnlM:T:", options, NULL)) != -1) {
 		switch (c) {
 			case 'b':
 				binary = 1;
@@ -225,6 +241,9 @@ iptables_restore_main(int argc, char *ar
 			case 'n':
 				noflush = 1;
 				break;
+			case 'l':
+				iptables_globals.exit_err = catch_exit_error;
+				break;
 			case 'M':
 				xtables_modprobe_program = optarg;
 				break;
@@ -437,8 +456,11 @@ iptables_restore_main(int argc, char *ar
 			for (a = 0; a < newargc; a++)
 				DEBUGP("argv[%u]: %s\n", a, newargv[a]);
 
-			ret = do_command4(newargc, newargv,
-					 &newargv[2], &handle, true);
+			if (!setjmp(jmp))
+				ret = do_command4(newargc, newargv,
+						 &newargv[2], &handle, true);
+			else
+				ret = 1;
 
 			free_argv();
 			fflush(stdout);