Blame tools/gmmproc.in

Packit 306c40
#! @PERL@
Packit 306c40
#
Packit 306c40
# @configure_input@
Packit 306c40
#
Packit 306c40
######################################################################
Packit 306c40
# gmmproc (version 4)
Packit 306c40
######################################################################
Packit 306c40
#
Packit 306c40
# *** WARNING: Only modify gmmproc.in. gmmproc is built. ***
Packit 306c40
#
Packit 306c40
# Copyright 2001, Karl Einar Nelson, Murray Cumming
Packit 306c40
#
Packit 306c40
# This program is free software; you can redistribute it and/or modify
Packit 306c40
# it under the terms of the GNU General Public License as published by
Packit 306c40
# the Free Software Foundation; either version 2 of the License, or 
Packit 306c40
# (at your option) any later version.
Packit 306c40
#
Packit 306c40
# This program is distributed in the hope that it will be useful,
Packit 306c40
# but WITHOUT ANY WARRANTY; without even the implied warranty of
Packit 306c40
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the 
Packit 306c40
# GNU General Public License for more details. 
Packit 306c40
#
Packit 306c40
# You should have received a copy of the GNU General Public License
Packit 306c40
# along with this program.  If not, see <http://www.gnu.org/licenses/>.
Packit 306c40
#
Packit 306c40
#
Packit 306c40
# 'classes':
Packit 306c40
# WrapParser: steps through .hg and .ccg files, outputting appropriate m4 code with Outputter.
Packit 306c40
# Outputter: Used by WrapParser to output wrapper code. Outputs *.g1 temp file
Packit 306c40
#            and uses m4 to generate *.g2 from it. Then outputs .h and .cc files.
Packit 306c40
# Function: Contains information about C and C++ functions and signals.
Packit 306c40
#
Packit 306c40
######################################################################
Packit 306c40
Packit 306c40
########################## 'main()' ##################################
Packit 306c40
Packit 306c40
$main::procdir;
Packit 306c40
$main::m4path;
Packit 306c40
$main::glibmm_version;
Packit 306c40
Packit 306c40
BEGIN {
Packit 306c40
  # get prefix info from configure
Packit 306c40
  my $prefix = "@prefix@";
Packit 306c40
  my $exec_prefix = "@exec_prefix@";
Packit 306c40
  my $libdir = "@libdir@";
Packit 306c40
Packit 306c40
  # This line must match the install directory
Packit 306c40
  $main::procdir = $libdir . '/@GLIBMM_MODULE_NAME@/proc';
Packit 306c40
  $main::m4path = "@M4@";
Packit 306c40
  $main::glibmm_version = "@PACKAGE_VERSION@";
Packit 306c40
Packit 306c40
  push(@INC, $main::procdir . '/pm');
Packit 306c40
}
Packit 306c40
Packit 306c40
use strict;
Packit 306c40
use warnings;
Packit 306c40
Packit 306c40
use Output;
Packit 306c40
use WrapParser;
Packit 306c40
Packit 306c40
# initialize globals 
Packit 306c40
@main::macrodirs         = ();
Packit 306c40
$main::srcdir            = '.';
Packit 306c40
$main::defsdir           = '.';
Packit 306c40
$main::source            = '';
Packit 306c40
$main::unwrapped         = 1;
Packit 306c40
$main::return_mismatches = (exists $ENV{'GMMPROC_RETURN_MISMATCHES'}) ? $ENV{'GMMPROC_RETURN_MISMATCHES'} : 0;
Packit 306c40
$main::debug             = (exists $ENV{'GMMPROC_DEBUG'}) ? $ENV{'GMMPROC_DEBUG'} : '';
Packit 306c40
Packit 306c40
# prototypes
Packit 306c40
sub parse_command_line_args();
Packit 306c40
Packit 306c40
#main()
Packit 306c40
parse_command_line_args();
Packit 306c40
Packit 306c40
my $objOutputter = &Output::new($main::m4path, \@main::macrodirs);
Packit 306c40
my $objWrapParser = &WrapParser::new($objOutputter);
Packit 306c40
Packit 306c40
$$objWrapParser{srcdir} = $main::srcdir;
Packit 306c40
$$objWrapParser{defsdir} = $main::defsdir;
Packit 306c40
$$objWrapParser{source} = $main::source;
Packit 306c40
$$objOutputter{source} = $main::source;
Packit 306c40
$$objOutputter{destdir} = $ARGV[1];
Packit 306c40
Packit 306c40
# Merge the C docs, e.g. gtk_docs.xml
Packit 306c40
Packit 306c40
# Suck the whole file into one big string, breaking it into tokens:
Packit 306c40
$objWrapParser->read_file($main::srcdir, $main::source);
Packit 306c40
Packit 306c40
# Parse output 
Packit 306c40
$objWrapParser->parse_and_build_output();
Packit 306c40
Packit 306c40
# Write out *.g1 temporary file:
Packit 306c40
$objOutputter->output_temp_g1($$objWrapParser{module}, $main::glibmm_version); # e.g. gtkmm, 2.38.0
Packit 306c40
Packit 306c40
# Execute m4 to get *.g2 file:
Packit 306c40
{
Packit 306c40
  my $exitcode = $objOutputter->make_g2_from_g1();
Packit 306c40
  if ($exitcode)
Packit 306c40
  {
Packit 306c40
    $objOutputter->remove_temp_files() unless ($main::debug);
Packit 306c40
Packit 306c40
    print STDERR "m4 failed with exit code $exitcode.  Aborting...\n";
Packit 306c40
    exit($exitcode);
Packit 306c40
  }
Packit 306c40
}
Packit 306c40
Packit 306c40
# Section out the resulting output
Packit 306c40
$objOutputter->write_sections_to_files();
Packit 306c40
$objOutputter->remove_temp_files() unless ($main::debug);
Packit 306c40
Packit 306c40
#Warn about any unwrapped function/signals:
Packit 306c40
if ($main::unwrapped)
Packit 306c40
{ 
Packit 306c40
  my @unwrapped = GtkDefs::get_unwrapped();
Packit 306c40
  @unwrapped = grep { exists $$_{entity_type} } @unwrapped;
Packit 306c40
Packit 306c40
  if (@unwrapped)
Packit 306c40
  {
Packit 306c40
    my @methods = grep { $$_{entity_type} eq 'method' and $$_{c_name} !~ m/^_/s } @unwrapped;
Packit 306c40
    my @signals = grep { $$_{entity_type} eq 'signal' } @unwrapped;
Packit 306c40
    # Don't take non-readable construct-only properties into account.
Packit 306c40
    my @properties = grep { $$_{entity_type} eq 'property' and ( $$_{readable} or not $$_{construct_only} ) } @unwrapped;
Packit 306c40
Packit 306c40
    # Don't print a name of any kind between the first and second colon on a line,
Packit 306c40
    # if there is any chance that "error" is (part of) the name.
Packit 306c40
    # MS Visual Studio will misunderstand.
Packit 306c40
    # See https://mail.gnome.org/archives/gtkmm-list/2014-November/msg00044.html
Packit 306c40
Packit 306c40
    local $, = "\ngmmproc:   ";
Packit 306c40
    local $\ = "\n";
Packit 306c40
Packit 306c40
    if (@methods)
Packit 306c40
    {
Packit 306c40
      print STDERR ("gmmproc, $main::source: Unwrapped functions:",
Packit 306c40
                    map($$_{c_name}, @methods));
Packit 306c40
    }
Packit 306c40
    if (@properties)
Packit 306c40
    {
Packit 306c40
      print STDERR ("gmmproc, $main::source: Unwrapped properties:",
Packit 306c40
                    map($$_{class} . '::' . $$_{name}, @properties));
Packit 306c40
    }
Packit 306c40
    if (@signals)
Packit 306c40
    { 
Packit 306c40
      print STDERR ("gmmproc, $main::source: Unwrapped signals:",
Packit 306c40
                    map($$_{class} . '::' . $$_{name}, @signals));
Packit 306c40
    }
Packit 306c40
  }
Packit 306c40
}
Packit 306c40
Packit 306c40
# end of program
Packit 306c40
exit;
Packit 306c40
Packit 306c40
Packit 306c40
####################################################################
Packit 306c40
Packit 306c40
Packit 306c40
sub print_usage()
Packit 306c40
{
Packit 306c40
  print
Packit 306c40
'Usage: gmmproc [options] name srcdir destdir
Packit 306c40
  -h 
Packit 306c40
  --help               This usage message.
Packit 306c40
Packit 306c40
  --doc                Produces a header file for documentation.  (FIXME)
Packit 306c40
Packit 306c40
  --debug              Leave intermediate output arround for analysis.
Packit 306c40
                       Alternatively, set GMMPROC_DEBUG=1 in the environment.
Packit 306c40
Packit 306c40
  --unwrapped          Warn about possible unwrapped functions.
Packit 306c40
Packit 306c40
  --return-mismatches  Warn about possible method return mismatches.
Packit 306c40
Packit 306c40
  --defs dir           Change the directory to seach for defs.
Packit 306c40
Packit 306c40
  -I dir               Specify the directory with m4 files.
Packit 306c40
Packit 306c40
Packit 306c40
Note: This will read srcdir/name.{hg,ccg} file and generates destdir/name.cc
Packit 306c40
';
Packit 306c40
  exit(1);
Packit 306c40
}
Packit 306c40
Packit 306c40
# void parse_command_line_args()
Packit 306c40
sub parse_command_line_args()
Packit 306c40
{
Packit 306c40
  print_usage() if ($#ARGV == -1);
Packit 306c40
Packit 306c40
  while ($#ARGV != -1)
Packit 306c40
  {
Packit 306c40
    $_ = shift @ARGV;
Packit 306c40
Packit 306c40
    if (/^-/)
Packit 306c40
    {
Packit 306c40
      print_usage() if ( /^--help/);
Packit 306c40
      print_usage() if ( /^-h/);
Packit 306c40
      if (/^-I/)
Packit 306c40
      {
Packit 306c40
        push @main::macrodirs, shift @ARGV;
Packit 306c40
      }
Packit 306c40
      elsif (/^--unwrapped/)
Packit 306c40
      {
Packit 306c40
        $main::unwrapped = 1;
Packit 306c40
      }
Packit 306c40
      elsif (/^--return-mismatches/)
Packit 306c40
      {
Packit 306c40
        $main::return_mismatches = 1;
Packit 306c40
      }
Packit 306c40
      elsif (/^--defs/)
Packit 306c40
      {
Packit 306c40
        $main::defsdir = shift @ARGV;
Packit 306c40
      }
Packit 306c40
      elsif (/^--debug/)
Packit 306c40
      {
Packit 306c40
        $main::debug = 1;
Packit 306c40
      }
Packit 306c40
      else
Packit 306c40
      {
Packit 306c40
        print "unknown parameter $_\n";
Packit 306c40
      }
Packit 306c40
      next;
Packit 306c40
    }
Packit 306c40
Packit 306c40
    last;
Packit 306c40
  }
Packit 306c40
Packit 306c40
  # we already have one argument
Packit 306c40
Packit 306c40
  if ($#ARGV != 1)
Packit 306c40
  {
Packit 306c40
    print STDERR ('Invalid number of arguments (', $#ARGV + 2, ")\n");
Packit 306c40
    print_usage();
Packit 306c40
  }
Packit 306c40
Packit 306c40
  $main::srcdir = $ARGV[0];
Packit 306c40
  $main::source = $_;
Packit 306c40
Packit 306c40
  push @main::macrodirs, $main::procdir . '/m4';
Packit 306c40
}