Fix code to work without executable stack

All local variables outside of the current function which are used by other
function are passed as pointers in function parameters. This change is
enough for avoiding need for executable stack for functions defined inside
another function.

Fixes error printed by kernel into dmesg every time when netplugd starts:
[   86.661478] process '/sbin/netplugd' started with executable stack

diff --git a/if_info.c b/if_info.c
index bb114f5200f3..9fb4012bdf1d 100644
--- a/if_info.c
+++ b/if_info.c
@@ -96,11 +96,11 @@ flags_str(char *buf, unsigned int fl)
 }
 
 void
-for_each_iface(int (*func)(struct if_info *))
+for_each_iface(int (*func)(struct if_info *, void *), void *arg)
 {
     for(int i = 0; i < INFOHASHSZ; i++) {
         for(struct if_info *info = if_info[i]; info != NULL; info = info->next) {
-            if ((*func)(info))
+            if ((*func)(info, arg))
                 return;
         }
     }
@@ -289,18 +289,24 @@ void ifsm_scriptdone(pid_t pid, int exitstatus)
 {
     int exitok = WIFEXITED(exitstatus) && WEXITSTATUS(exitstatus) == 0;
     struct if_info *info;
+    void *arg[2];
     assert(WIFEXITED(exitstatus) || WIFSIGNALED(exitstatus));
 
-    int find_pid(struct if_info *i) {
+    int find_pid(struct if_info *i, void *arg) {
+        pid_t pid = *(pid_t *)(((void **)arg)[0]);
+        struct if_info **info = (struct if_info **)(((void **)arg)[0]);
+
         if (i->worker == pid) {
-            info = i;
+            *info = i;
             return 1;
         }
         return 0;
     }
 
     info = NULL;
-    for_each_iface(find_pid);
+    arg[0] = &pid;
+    arg[1] = &info;
+    for_each_iface(find_pid, arg);
 
     if (info == NULL) {
         do_log(LOG_INFO, "Unexpected child %d exited with status %d",
diff --git a/main.c b/main.c
index a3cdf635f2ca..f95e2f9dbdde 100644
--- a/main.c
+++ b/main.c
@@ -191,7 +191,8 @@ poll_interfaces(void)
         close_on_exec(sockfd);
     }
 
-    int pollflags(struct if_info *info) {
+    int pollflags(struct if_info *info, void *arg) {
+        int sockfd = *(int *)arg;
         struct ifreq ifr;
 
         if (!if_match(info->name))
@@ -207,8 +208,7 @@ poll_interfaces(void)
 
         return 0;
     }
-
-    for_each_iface(pollflags);
+    for_each_iface(pollflags, &sockfd);
 }
 
 int debug = 0;
@@ -349,12 +349,12 @@ main(int argc, char *argv[])
         /* Run over each of the interfaces we know and care about, and
            make sure the state machine has done the appropriate thing
            for their current state. */
-        int poll_flags(struct if_info *i) {
+        int poll_flags(struct if_info *i, void *arg) {
             if (if_match(i->name))
                 ifsm_flagpoll(i);
             return 0;
         }
-        for_each_iface(poll_flags);
+        for_each_iface(poll_flags, NULL);
     }
 
     for(;;) {
diff --git a/netplug.h b/netplug.h
index 1f041ca0ffe0..b66ae9e36b30 100644
--- a/netplug.h
+++ b/netplug.h
@@ -83,7 +83,7 @@ struct if_info *if_info_update_interface(struct nlmsghdr *hdr,
                                          struct rtattr *attrs[]);
 int if_info_save_interface(struct nlmsghdr *hdr, void *arg);
 void parse_rtattrs(struct rtattr *tb[], int max, struct rtattr *rta, int len);
-void for_each_iface(int (*func)(struct if_info *));
+void for_each_iface(int (*func)(struct if_info *, void *), void *arg);
 
 void ifsm_flagpoll(struct if_info *info);
 void ifsm_flagchange(struct if_info *info, unsigned int newflags);
