[gobject-introspection] scanner: Add --symbol-filter-cmd



commit 7e5a553e7b597a7d53e901307c5f46a660b9c124
Author: Garrett Regier <garrett regier riftio com>
Date:   Sat Feb 14 11:15:50 2015 -0800

    scanner: Add --symbol-filter-cmd
    
    Add the command line flag --symbol-filter-cmd to g-ir-scanner
    which allows running symbol names through a filtering shell
    command. The symbol is sent as stdin to the filter command
    and expects a filtered result written to stdout.
    
    https://bugzilla.gnome.org/show_bug.cgi?id=744534
    Signed-off-by: Garrett Regier <garrett regier riftio com>

 .gitignore                                  |    1 +
 giscanner/scannermain.py                    |    8 ++++-
 giscanner/transformer.py                    |   16 +++++++++-
 tests/scanner/Makefile.am                   |   14 ++++++++
 tests/scanner/Symbolfilter-1.0-expected.gir |   45 +++++++++++++++++++++++++++
 tests/scanner/symbolfilter.h                |   10 ++++++
 tests/scanner/symbolfilter.py               |   38 ++++++++++++++++++++++
 7 files changed, 130 insertions(+), 2 deletions(-)
---
diff --git a/.gitignore b/.gitignore
index dc5361c..7551c4a 100644
--- a/.gitignore
+++ b/.gitignore
@@ -83,6 +83,7 @@ tests/scanner/Utility-1.0.gir
 tests/scanner/WarnLib-1.0.gir
 tests/scanner/barapp
 tests/scanner/Identfilter-1.0.gir
+tests/scanner/Symbolfilter-1.0.gir
 tests/scanner/Typedefs-1.0.gir
 tests/doctool/DocExamples-1.0.gir
 tests/offsets/Offsets-1.0.gir
diff --git a/giscanner/scannermain.py b/giscanner/scannermain.py
index b36284d..6be958e 100755
--- a/giscanner/scannermain.py
+++ b/giscanner/scannermain.py
@@ -164,6 +164,11 @@ the latter is not specified.""")
     parser.add_option("", "--symbol-prefix",
                       action="append", dest="symbol_prefixes", default=[],
                       help="Remove this prefix from C symbols (function names)")
+    parser.add_option("", "--symbol-filter-cmd",
+                      action="store", dest="symbol_filter_cmd", default='',
+                      help='Filter symbols (function names) through the given '
+                           'shell command which will receive the symbol name as input '
+                           'to stdin and is expected to output the filtered results to stdout.')
     parser.add_option("", "--accept-unprefixed",
                       action="store_true", dest="accept_unprefixed", default=False,
                       help="""If specified, accept symbols and identifiers that do not
@@ -367,7 +372,8 @@ see --identifier-prefix and --symbol-prefix."""
 def create_transformer(namespace, options):
     transformer = Transformer(namespace,
                               accept_unprefixed=options.accept_unprefixed,
-                              identifier_filter_cmd=options.identifier_filter_cmd)
+                              identifier_filter_cmd=options.identifier_filter_cmd,
+                              symbol_filter_cmd=options.symbol_filter_cmd)
     transformer.set_include_paths(options.include_paths)
     if options.passthrough_gir:
         transformer.disable_cache()
diff --git a/giscanner/transformer.py b/giscanner/transformer.py
index b8bdfba..6ae6389 100644
--- a/giscanner/transformer.py
+++ b/giscanner/transformer.py
@@ -50,7 +50,8 @@ if os.name != 'nt':
 class Transformer(object):
     namespace = property(lambda self: self._namespace)
 
-    def __init__(self, namespace, accept_unprefixed=False, identifier_filter_cmd=''):
+    def __init__(self, namespace, accept_unprefixed=False,
+                 identifier_filter_cmd='', symbol_filter_cmd=''):
         self._cachestore = CacheStore()
         self._accept_unprefixed = accept_unprefixed
         self._namespace = namespace
@@ -60,6 +61,7 @@ class Transformer(object):
         self._includepaths = []
         self._passthrough_mode = False
         self._identifier_filter_cmd = identifier_filter_cmd
+        self._symbol_filter_cmd = symbol_filter_cmd
 
         # Cache a list of struct/unions in C's "tag namespace". This helps
         # manage various orderings of typedefs and structs. See:
@@ -242,6 +244,18 @@ currently-scanned namespace is first."""
         return cmp(x[2], y[2])
 
     def _split_c_string_for_namespace_matches(self, name, is_identifier=False):
+        if not is_identifier and self._symbol_filter_cmd:
+            proc = subprocess.Popen(self._symbol_filter_cmd,
+                                    stdin=subprocess.PIPE,
+                                    stdout=subprocess.PIPE,
+                                    stderr=subprocess.PIPE,
+                                    shell=True)
+            _name = name
+            name, err = proc.communicate(name)
+            if proc.returncode:
+                raise ValueError('filter: "%s" exited: %d with error: %s' %
+                                 (self._symbol_filter_cmd, proc.returncode, err))
+
         matches = []  # Namespaces which might contain this name
         unprefixed_namespaces = []  # Namespaces with no prefix, last resort
         for ns in self._iter_namespaces():
diff --git a/tests/scanner/Makefile.am b/tests/scanner/Makefile.am
index 2b3188e..92a22c3 100644
--- a/tests/scanner/Makefile.am
+++ b/tests/scanner/Makefile.am
@@ -188,6 +188,20 @@ Identfilter-1.0.gir: identfilter.h
                --identifier-filter-cmd="$(PYTHON) $(srcdir)/identfilter.py" \
                --output=$@ $<
 
+EXTRA_DIST += \
+       symbolfilter.py \
+       symbolfilter.h \
+       Symbolfilter-1.0-expected.gir
+CLEANFILES += Symbolfilter-1.0.gir
+CHECKGIRS += Symbolfilter-1.0.gir
+
+Symbolfilter-1.0.gir: symbolfilter.h
+       $(AM_V_GEN) $(INTROSPECTION_SCANNER) $(INTROSPECTION_SCANNER_ARGS) \
+               --warn-all --reparse-validate \
+               --namespace=Symbolfilter --accept-unprefixed --nsversion=1.0 --header-only \
+               --symbol-filter-cmd="$(PYTHON) $(srcdir)/symbolfilter.py" \
+               --output=$@ $<
+
 if BUILD_DOCTOOL
 DOCGIRS = Regress-1.0.gir
 CHECKDOCS = $(DOCGIRS:.gir=-C) $(DOCGIRS:.gir=-Python) $(DOCGIRS:.gir=-Gjs) $(DOCGIRS:.gir=-sections.txt)
diff --git a/tests/scanner/Symbolfilter-1.0-expected.gir b/tests/scanner/Symbolfilter-1.0-expected.gir
new file mode 100644
index 0000000..db063d1
--- /dev/null
+++ b/tests/scanner/Symbolfilter-1.0-expected.gir
@@ -0,0 +1,45 @@
+<?xml version="1.0"?>
+<!-- This file was automatically generated from C sources - DO NOT EDIT!
+To affect the contents of this file, edit the original C definitions,
+and/or use gtk-doc annotations.  -->
+<repository version="1.2"
+            xmlns="http://www.gtk.org/introspection/core/1.0";
+            xmlns:c="http://www.gtk.org/introspection/c/1.0";
+            xmlns:glib="http://www.gtk.org/introspection/glib/1.0";>
+  <namespace name="Symbolfilter"
+             version="1.0"
+             shared-library=""
+             c:identifier-prefixes="Symbolfilter"
+             c:symbol-prefixes="symbolfilter">
+    <record name="Object" c:type="SymbolfilterObject" disguised="1">
+      <method name="filterObjectFooMethod"
+              c:identifier="SymbolfilterObjectFooMethod">
+        <return-value transfer-ownership="none">
+          <type name="none" c:type="void"/>
+        </return-value>
+        <parameters>
+          <instance-parameter name="self" transfer-ownership="none">
+            <type name="Object" c:type="SymbolfilterObject*"/>
+          </instance-parameter>
+        </parameters>
+      </method>
+      <method name="filterObjectFree" c:identifier="SymbolfilterObjectFree">
+        <return-value transfer-ownership="none">
+          <type name="none" c:type="void"/>
+        </return-value>
+        <parameters>
+          <instance-parameter name="self" transfer-ownership="none">
+            <type name="Object" c:type="SymbolfilterObject*"/>
+          </instance-parameter>
+        </parameters>
+      </method>
+      <function name="new"
+                c:identifier="SymbolfilterObjectNew"
+                introspectable="0">
+        <return-value>
+          <type name="Object" c:type="SymbolfilterObject*"/>
+        </return-value>
+      </function>
+    </record>
+  </namespace>
+</repository>
diff --git a/tests/scanner/symbolfilter.h b/tests/scanner/symbolfilter.h
new file mode 100644
index 0000000..f42dfb3
--- /dev/null
+++ b/tests/scanner/symbolfilter.h
@@ -0,0 +1,10 @@
+#ifndef __SYMBOLFILTER_H__
+#define __SYMBOLFILTER_H__
+
+typedef struct _SymbolfilterObject SymbolfilterObject;
+
+SymbolfilterObject *SymbolfilterObjectNew (void);
+void SymbolfilterObjectFooMethod (SymbolfilterObject *self);
+void SymbolfilterObjectFree (SymbolfilterObject *self);
+
+#endif
diff --git a/tests/scanner/symbolfilter.py b/tests/scanner/symbolfilter.py
new file mode 100644
index 0000000..589d0b7
--- /dev/null
+++ b/tests/scanner/symbolfilter.py
@@ -0,0 +1,38 @@
+# -*- Mode: Python; py-indent-offset: 4 -*-
+# vim: tabstop=4 shiftwidth=4 expandtab
+#
+# Copyright (C) 2015 Garrett Regier <garrett regier riftio com>
+#
+# This library is free software; you can redistribute it and/or
+# modify it under the terms of the GNU Lesser General Public
+# License as published by the Free Software Foundation; either
+# version 2.1 of the License, or (at your option) any later version.
+#
+# This library is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+# Lesser General Public License for more details.
+#
+# You should have received a copy of the GNU Lesser General Public
+# License along with this library; if not, write to the Free Software
+# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301
+# USA
+
+"""
+Script which reads symbols in the form of "FooBar" from stdin and
+translates them to snake case like "foo_bar".
+"""
+
+import sys
+
+
+def ensure_snake_case(text):
+    text = ''.join(x if x.islower() else '_' + x.lower() for x in text)
+
+    # Remove the extra '_' for the starting uppercase letter
+    return text[1:]
+
+
+if __name__ == '__main__':
+    text = ensure_snake_case(sys.stdin.read())
+    sys.stdout.write(text)


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]