mingw32 packaging review
by Adam Stokes
Hi,
Packaged up netcf for windows would like a review over the spec and the makefiles
http://astokes.fedorapeople.org/mingw32-netcf/
--
__ __
.-----.| |_.-----.| |--.-----.-----.
|__ --|| _| _ || <| -__|__ --|
|_____||____|_____||__|__|_____|_____|
.----------------------------------.
( ajs(a)redhat.com || 919.754.4187 )
`----------------------------------'
13 years, 8 months
[PATCH] Don't delete the physical interface config when defining a vlan.
by Laine Stump
Prior to defining a new interface, drv_define() would previously call
rm_all_interfaces(), which would look for all nodes called "interface"
at every level, and remove the config for any existing interface with
the same name. This is necessary when defining a bridge or a bond
(since those interfaces will now be slaves of the toplevel
bridge/bond, and their config will be created anew along with the
toplevel), but is the wrong thing to do for vlans - not only does the
physical interface associated with a vlan have an existence of its
own, multiple vlans can be associated with the same physical
interface, and the act of defining a vlan *does not* re-create the
physical interface config. The result of this was dismal failure when
attempting to define a vlan interface - the associated physical
interface would disappear.
To solve this problem, rm_all_interfaces() has been replaced with
rm_interface_and_slaves(), which removes the config for the toplevel
interface, the checks to see if it is a bridge or a bond; if so, it
also removes the config for any interfaces slaved to this
bridge/bond.
Because a bridge may enslave a bond, which in turn may enslave
physical interfaces, this function was made recursive.
---
src/drv_initscripts.c | 100 ++++++++++++++++++++++++++++++++++++++-----------
1 files changed, 78 insertions(+), 22 deletions(-)
diff --git a/src/drv_initscripts.c b/src/drv_initscripts.c
index d5bbd44..389dbb6 100644
--- a/src/drv_initscripts.c
+++ b/src/drv_initscripts.c
@@ -936,34 +936,90 @@ static void rm_interface(struct netcf *ncf, const char *name) {
FREE(path);
}
-/* Remove all interfaces and their slaves mentioned in NCF_XML. We need to
- * remove interfaces one by one when we define an interface, since what
- * will become a subinterface may not be related to the new toplevel
- * interface, and calling RM_INTERFACE on the toplevel interface is
- * therefore not enough.
+
+/* rm_interface_and_slaves_helper()
+ *
+ * Given a context pointing to an "interface" node, delete the config
+ * for the interface with the name of this node's "name" property.
+ * Then, if this node's type is "bridge" or "bond", cycle through
+ * all "type"/interface subnodes and call this function to delete
+ * their config as well.
*/
-static void rm_all_interfaces(struct netcf *ncf, xmlDocPtr ncf_xml) {
- xmlXPathContextPtr context = NULL;
- xmlXPathObjectPtr obj = NULL;
+static void rm_interface_and_slaves_helper(struct netcf *ncf,
+ xmlDocPtr ncf_xml,
+ xmlXPathContextPtr ctxt) {
+ xmlNodePtr save_node = ctxt->node;
+ xmlXPathObjectPtr obj = NULL;
+ xmlChar *name = NULL, *type = NULL;
+ char *if_node_exp = NULL;
+
+ xmlNodeSetPtr ns;
+
+ /* remove the top-level interface */
+ name = xmlGetProp(ctxt->node, BAD_CAST "name");
+ ERR_NOMEM(name == NULL, ncf);
+ rm_interface(ncf, (char *) name);
+ ERR_BAIL(ncf);
- context = xmlXPathNewContext(ncf_xml);
- ERR_NOMEM(context == NULL, ncf);
+ type = xmlGetProp(ctxt->node, BAD_CAST "type");
+ ERR_NOMEM(name == NULL, ncf);
- obj = xmlXPathEvalExpression(BAD_CAST "//interface", context);
- ERR_NOMEM(obj == NULL, ncf);
+ if (xmlStrEqual(type, BAD_CAST "bridge")
+ || xmlStrEqual(type, BAD_CAST "bond")) {
+ /* get a list of all interface subnodes under
+ * this interface's "type" node.
+ * eg "./bond/interface"
+ */
+
+ int r = xasprintf(&if_node_exp, "./%s/interface", (char *)type);
+ ERR_NOMEM(r < 0, ncf);
+
+ obj = xmlXPathEvalExpression(BAD_CAST if_node_exp, ctxt);
+ ERR_NOMEM(obj == NULL, ncf);
+ ns = obj->nodesetval;
+ ERR_NOMEM(ns == NULL, ncf);
+
+ /* iterate through them all, removing them as we go */
+ for (int ii=0; ii < ns->nodeNr; ii++) {
+
+ ERR_NOMEM(ns->nodeTab[ii] == NULL, ncf);
+
+ /* make this interface the toplevel node & recurse */
+ ctxt->node = ns->nodeTab[ii];
+ rm_interface_and_slaves_helper(ncf, ncf_xml, ctxt);
+ ERR_BAIL(ncf);
+ }
+ }
- xmlNodeSetPtr ns = obj->nodesetval;
- for (int i=0; i < ns->nodeNr; i++) {
- xmlChar *name = xmlGetProp(ns->nodeTab[i], BAD_CAST "name");
- ERR_NOMEM(name == NULL, ncf);
- rm_interface(ncf, (char *) name);
- xmlFree(name);
- ERR_BAIL(ncf);
- }
error:
xmlXPathFreeObject(obj);
- xmlXPathFreeContext(context);
+ FREE(if_node_exp);
+ xmlFree(name);
+ xmlFree(type);
+ ctxt->node = save_node;
+}
+
+/* Remove the toplevel interface, and all slaves recursively. We need to
+ * remove interfaces one by one when we define an interface, since what
+ * will become a subinterface may not be related to the new toplevel
+ * interface, and calling RM_INTERFACE on the toplevel interface is
+ * therefore not enough.
+ *
+ * This function just sets up the initial context and calls the helper
+ * function above, which does the real work.
+ */
+static void rm_interface_and_slaves(struct netcf *ncf, xmlDocPtr ncf_xml) {
+ xmlXPathContextPtr ctxt;
+
+ ctxt = xmlXPathNewContext(ncf_xml);
+ ERR_NOMEM(ctxt == NULL, ncf);
+
+ ctxt->node = xmlDocGetRootElement(ncf_xml);
+ if (xmlStrEqual(ctxt->node->name, BAD_CAST "interface"))
+ rm_interface_and_slaves_helper(ncf, ncf_xml, ctxt);
+error:
+ xmlXPathFreeContext(ctxt);
}
/* Dig through interface NAME and all its subinterfaces for bonds
@@ -1017,7 +1073,7 @@ struct netcf_if *drv_define(struct netcf *ncf, const char *xml_str) {
name = device_name_from_xml(ncf, ncf_xml);
ERR_COND_BAIL(name == NULL, ncf, EINTERNAL);
- rm_all_interfaces(ncf, ncf_xml);
+ rm_interface_and_slaves(ncf, ncf_xml);
ERR_BAIL(ncf);
aug_xml = apply_stylesheet(ncf, ncf->driver->get, ncf_xml);
--
1.7.1.1
13 years, 9 months
defined DATADIR conflicts with objidl.h during mingw compile
by Adam Stokes
Hi,
Using the defined DATADIR from datadir.h mingw will croak on compile. My suggestion would be to at least rename DATADIR within datadir.h to something else not referenced:
src/Makefile.am
datadir.h: $(top_builddir)/config.status
>-------echo '#define DATADIR "$(datadir)"' > datadir.h
objidl.h
typedef enum tagDATADIR>{
>-------DATADIR_GET=1,
>-------DATADIR_SET
} DATADIR;
Any suggestions on how we want to approach this?
Thanks!
--
__ __
.-----.| |_.-----.| |--.-----.-----.
|__ --|| _| _ || <| -__|__ --|
|_____||____|_____||__|__|_____|_____|
.----------------------------------.
( ajs(a)redhat.com || 919.754.4187 )
`----------------------------------'
13 years, 9 months
portability make issues
by Adam Stokes
Hi,
Im a little stuck as to what this error is referring to during a mingw32 compile:
No implicit rule found for `-L/usr/i686-pc-mingw32/sys-root/mingw/lib'.
Finished prerequisites of target file `-L/usr/i686-pc-mingw32/sys-root/mingw/lib'.
Must remake target `-L/usr/i686-pc-mingw32/sys-root/mingw/lib'.
make[1]: Entering directory `/home/akimbo/Documents/dev/netcf-bm/src'
make[1]: *** No rule to make target `-L/usr/i686-pc-mingw32/sys-root/mingw/lib', needed by `libnetcf.la'. Stop.
make[1]: Leaving directory `/home/akimbo/Documents/dev/netcf-bm/src'
Reaping losing child 0x092f1818 PID 2841
make: *** [all] Error 2
Removing child 0x092f1818 PID 2841 from chain.
I'm attaching both config.log and the full output from make -d within the src dir.
im keeping a separate codebase over at http://github.com/battlemidget/netcf-bm which will give you an idea of the gnulib modules i've included to overcome some of the portability issues and various changes applied to configure.ac for leaving out the initscript code on win32.
thanks
--
__ __
.-----.| |_.-----.| |--.-----.-----.
|__ --|| _| _ || <| -__|__ --|
|_____||____|_____||__|__|_____|_____|
.----------------------------------.
( ajs(a)redhat.com || 919.754.4187 )
`----------------------------------'
13 years, 9 months
[PATCH] Properly handle quoted entries in sysconfig files
by David Lutterkort
From: David Lutterkort <lutter(a)redhat.com>
The Augeas lens we used (Shellvars), maps an entry like
DEVICE="eth0"
into the tree including quotes. That leads to problems down the road, since
the quotes become part of the interface name.
To address that, we use a lens (Sysconfig) that is more geared towards the
subset of shell syntax used in sysconfig files. It strips quotes when
reading files and adds and restores them as needed.
* data/lenses/sysconfig.aug: lens for sysconfig files that strips
quotes from values
* data/lenses/tests/test_sysconfig.aug: tests for Sysconfig lens,
especially for handling all the corner cases with quoted strings
* src/drv_initscripts.c (augeas_xfm_common_pv): use Sysconfig lens,
not Shellvars lens
* Makefile.am: install Sysconfig lens
* tests/root/etc/sysconfig/network-scripts/ifcfg-br0: add unnecessary
quotes
Fixes BZ 613886
---
Makefile.am | 2 +-
data/lenses/sysconfig.aug | 60 +++++++++++
data/lenses/tests/test_sysconfig.aug | 110 ++++++++++++++++++++
src/drv_initscripts.c | 2 +-
tests/root/etc/sysconfig/network-scripts/ifcfg-br0 | 11 +-
5 files changed, 178 insertions(+), 7 deletions(-)
create mode 100644 data/lenses/sysconfig.aug
create mode 100644 data/lenses/tests/test_sysconfig.aug
diff --git a/Makefile.am b/Makefile.am
index d61a752..416a9ad 100644
--- a/Makefile.am
+++ b/Makefile.am
@@ -15,7 +15,7 @@ dist_xml_DATA=data/xml/augeas.rng data/xml/interface.rng \
data/xml/util-get.xsl data/xml/util-put.xsl \
data/xml/initscripts-get.xsl data/xml/initscripts-put.xsl
dist_netcf_DATA=data/iptables-forward-bridged
-dist_lens_DATA=data/lenses/netcf.aug
+dist_lens_DATA=data/lenses/netcf.aug data/lenses/sysconfig.aug
# This requires that trang is installed, but we don't want to require
# that, even for building, since the .rnc files are only a convenience
diff --git a/data/lenses/sysconfig.aug b/data/lenses/sysconfig.aug
new file mode 100644
index 0000000..9ee668e
--- /dev/null
+++ b/data/lenses/sysconfig.aug
@@ -0,0 +1,60 @@
+(* Variation of the Shellvars lens *)
+(* Supports only what's needed to handle sysconfig files *)
+(* Modified to strip quotes. In the put direction, add double quotes *)
+(* around values that need them *)
+(* To keep things simple, we also do not support shell variable arrays *)
+module Sysconfig =
+ let eol = Util.eol
+
+ let key_re = /[A-Za-z0-9_]+(\[[0-9]+\])?/ - "unset" - "export"
+ let eq = Util.del_str "="
+ let comment = Util.comment
+ let empty = Util.empty
+ let xchgs = Build.xchgs
+ let dels = Util.del_str
+
+ let nothing = del /(""|'')?/ "" . value ""
+
+ (* Chars allowed in a bare string *)
+ let bchar = /[^ \t\n\"'\\]|\\\\./
+ let qchar = /["']/ (* " *)
+
+ (* We split the handling of right hand sides into a few cases:
+ * bare - strings that contain no spaces, optionally enclosed in
+ * single or double quotes
+ * dquot - strings that contain at least one space or apostrophe,
+ * which must be enclosed in double quotes
+ * squot - strings that contain an unescaped double quote
+ *)
+ let bare = del qchar? "" . store (bchar+) . del qchar? ""
+ let dquot =
+ del qchar "\"" . store (bchar* . /[ \t']/ . bchar*)+ . del qchar "\""
+ let squot =
+ dels "'" . store ((bchar|/[ \t]/)* . "\"" . (bchar|/[ \t]/)*)+ . dels "'"
+
+ let export = [ key "export" . Util.del_ws_spc ]
+ let kv (value:lens) = [ export? . key key_re . eq . value . eol ]
+ let assign = kv nothing | kv bare | kv dquot | kv squot
+
+ let var_action (name:string) =
+ [ xchgs name ("@" . name) . Util.del_ws_spc . store key_re . eol ]
+
+ let unset = var_action "unset"
+ let bare_export = var_action "export"
+
+ let source =
+ [
+ del /\.|source/ "." . label ".source" .
+ Util.del_ws_spc . store /[^= \t\n]+/ . eol
+ ]
+
+ let lns = (comment | empty | source | assign | unset | bare_export) *
+
+(*
+ Examples:
+
+ abc -> abc -> abc
+ "abc" -> abc -> abc
+ "a b" -> a b -> "a b"
+ 'a"b' -> a"b -> 'a"b'
+*)
diff --git a/data/lenses/tests/test_sysconfig.aug b/data/lenses/tests/test_sysconfig.aug
new file mode 100644
index 0000000..ef8abd4
--- /dev/null
+++ b/data/lenses/tests/test_sysconfig.aug
@@ -0,0 +1,110 @@
+(* Test for sysconfig lens *)
+module Test_sysconfig =
+
+ let eth_static = "# Intel Corporation PRO/100 VE Network Connection
+DEVICE=eth0
+BOOTPROTO=static
+BROADCAST=172.31.0.255
+HWADDR=ab:cd:ef:12:34:56
+export IPADDR=172.31.0.31
+#DHCP_HOSTNAME=host.example.com
+NETMASK=255.255.255.0
+NETWORK=172.31.0.0
+unset ONBOOT
+"
+ let empty_val = "EMPTY=\nDEVICE=eth0\n"
+
+ let key_brack = "SOME_KEY[1]=\nDEVICE=eth0\n"
+
+ test Sysconfig.lns get eth_static =
+ { "#comment" = "Intel Corporation PRO/100 VE Network Connection" }
+ { "DEVICE" = "eth0" }
+ { "BOOTPROTO" = "static" }
+ { "BROADCAST" = "172.31.0.255" }
+ { "HWADDR" = "ab:cd:ef:12:34:56" }
+ { "IPADDR" = "172.31.0.31"
+ { "export" } }
+ { "#comment" = "DHCP_HOSTNAME=host.example.com" }
+ { "NETMASK" = "255.255.255.0" }
+ { "NETWORK" = "172.31.0.0" }
+ { "@unset" = "ONBOOT" }
+
+ test Sysconfig.lns put eth_static after
+ set "BOOTPROTO" "dhcp" ;
+ rm "IPADDR" ;
+ rm "BROADCAST" ;
+ rm "NETMASK" ;
+ rm "NETWORK"
+ = "# Intel Corporation PRO/100 VE Network Connection
+DEVICE=eth0
+BOOTPROTO=dhcp
+HWADDR=ab:cd:ef:12:34:56
+#DHCP_HOSTNAME=host.example.com
+unset ONBOOT
+"
+ test Sysconfig.lns get empty_val =
+ { "EMPTY" = "" } { "DEVICE" = "eth0" }
+
+ test Sysconfig.lns get key_brack =
+ { "SOME_KEY[1]" = "" } { "DEVICE" = "eth0" }
+
+ test Sysconfig.lns get "smartd_opts=\"-q never\"\n" =
+ { "smartd_opts" = "-q never" }
+
+ test Sysconfig.lns get "var=val \n" = { "var" = "val" }
+
+ test Sysconfig.lns get ". /etc/java/java.conf\n" =
+ { ".source" = "/etc/java/java.conf" }
+
+ (* Quoted strings and other oddities *)
+ test Sysconfig.lns get "var=\"foo 'bar'\"\n" =
+ { "var" = "foo 'bar'" }
+
+ test Sysconfig.lns get "var=\"eth0\"\n" =
+ { "var" = "eth0" }
+
+ test Sysconfig.lns get "var='eth0'\n" =
+ { "var" = "eth0" }
+
+ test Sysconfig.lns get "var='Some \"funny\" value'\n" =
+ { "var" = "Some \"funny\" value" }
+
+ test Sysconfig.lns get "var=\"\\\"\"\n" =
+ { "var" = "\\\"" }
+
+ test Sysconfig.lns get "var=\\\"\n" =
+ { "var" = "\\\"" }
+
+ test Sysconfig.lns get "var=ab#c\n" =
+ { "var" = "ab#c" }
+
+ (* We don't handle backticks *)
+ test Sysconfig.lns get
+ "var=`grep nameserver /etc/resolv.conf | head -1`\n" = *
+
+ (* We don't handle comments at the end of a line yet *)
+ test Sysconfig.lns get "var=ab #c\n" = *
+
+ (* Bug 109: allow a bare export *)
+ test Sysconfig.lns get "export FOO\n" =
+ { "@export" = "FOO" }
+
+ (* Check we put quotes in when changes require them *)
+ test Sysconfig.lns put "var=\"v\"\n" after rm "/foo" =
+ "var=\"v\"\n"
+
+ test Sysconfig.lns put "var=v\n" after set "/var" "v w"=
+ "var=\"v w\"\n"
+
+ test Sysconfig.lns put "var='v'\n" after set "/var" "v w"=
+ "var='v w'\n"
+
+ test Sysconfig.lns put "var=v\n" after set "/var" "v'w"=
+ "var=\"v'w\"\n"
+
+ test Sysconfig.lns put "var=v\n" after set "/var" "v\"w"=
+ "var='v\"w'\n"
+
+(* Local Variables: *)
+(* mode: caml *)
+(* End: *)
diff --git a/src/drv_initscripts.c b/src/drv_initscripts.c
index 6a1453a..d5bbd44 100644
--- a/src/drv_initscripts.c
+++ b/src/drv_initscripts.c
@@ -56,7 +56,7 @@ static const char *const ifcfg_path =
/* Augeas should only load the files we are interested in */
static const struct augeas_pv augeas_xfm_common_pv[] = {
/* Ifcfg files */
- { "/augeas/load/Ifcfg/lens", "Shellvars.lns" },
+ { "/augeas/load/Ifcfg/lens", "Sysconfig.lns" },
{ "/augeas/load/Ifcfg/incl",
"/etc/sysconfig/network-scripts/ifcfg-*" },
{ "/augeas/load/Ifcfg/excl[1]", "*~" },
diff --git a/tests/root/etc/sysconfig/network-scripts/ifcfg-br0 b/tests/root/etc/sysconfig/network-scripts/ifcfg-br0
index 37bfe89..d4bbc65 100644
--- a/tests/root/etc/sysconfig/network-scripts/ifcfg-br0
+++ b/tests/root/etc/sysconfig/network-scripts/ifcfg-br0
@@ -1,5 +1,6 @@
-DEVICE=br0
-ONBOOT=yes
-BOOTPROTO=dhcp
-TYPE=Bridge
-DELAY=0
+# Enclosing the values in useless quotes is intentional
+DEVICE="br0"
+ONBOOT='yes'
+BOOTPROTO="dhcp"
+TYPE="Bridge"
+DELAY='0'
--
1.7.1.1
13 years, 9 months
[SOLVED] netcf 0.1.6 and libxml2 issues in Centos5
by Sergio Rubio
Hi all,
First of all, my apologies for posting this to the devel list
(couldn't find the -users list).
I'm trying to use netcf 0.1.6 in CentOS 5 in combination with libvirt
0.8.1. Everything works ok so far.
When I try to create a new bridge interface using "ncftool define" I
get the following error:
error: XML invalid
error: Element interface failed to validate attributes
I´ve verified that this interface definition file works in FC13:
http://gist.github.com/461219
The solution, upgrade libxml2 to a newer version (tested with libxml2 2.7.7)
I´ve got updated libvirt+netcf+libxml2+libnl packages for CentOS5.
Hope someone finds this useful.
Regards.
13 years, 9 months