view release on metacpan or search on metacpan
Revision history for Clang
0.09 2015-06-20 18:48:51+02:00 Europe/Rome
- Add methods to determine whether a cursor represents a virtual method
or a pure virtual method (GH#5) (thanks, @ArthurJahn!)
- Add method to get a cursor's number of arguments (GH#5)
(thanks, @Ziul, @LucianoAlmeida!)
0.08 2015-05-26 14:00:26+02:00 Europe/Rome
- Return cursor's final line and column from Cursor -> location()
(GH#3) (thanks, @gutorc92!)
- Add method to retrieve cursor's access specifier (GH#4)
(thanks, @gutorc92 and @lucasmoura!)
0.07 2015-04-23 20:09:52+02:00 Europe/Rome
- Build with libclang v3.5 (GH#2) (thanks, @ArthurJahn!)
- Do not suggest perl version in the example
- Various test fixes
0.06 2012-08-20 13:20:25 Europe/Rome
#include <clang-c/Index.h>
typedef CXIndex Index;
typedef CXTranslationUnit TUnit;
typedef CXCursor * Cursor;
typedef enum CXCursorKind CursorKind;
typedef CXType * Type;
typedef enum CXTypeKind TypeKind;
typedef CXDiagnostic Diagnostic;
enum CXChildVisitResult visitor(CXCursor cursor, CXCursor parent, CXClientData data) {
SV *child;
AV *children = data;
CXCursor *ref = malloc(sizeof(CXCursor));
*ref = cursor;
child = sv_setref_pv(newSV(0), "Clang::Cursor", (void *) ref);
av_push(children, child);
return CXChildVisit_Continue;
}
MODULE = Clang PACKAGE = Clang
lib/Clang.pm
lib/Clang/Cursor.pm
lib/Clang/CursorKind.pm
lib/Clang/Diagnostic.pm
lib/Clang/Index.pm
lib/Clang/TUnit.pm
lib/Clang/Type.pm
lib/Clang/TypeKind.pm
t/00-compile.t
t/01-tunit.t
t/02-cursor.t
t/03-cursorkind.t
t/05-typekind.t
t/06-diagnostic.t
t/fragments/animal.h
t/fragments/cat.cc
t/fragments/cat.h
t/fragments/main.cpp
t/fragments/mammal.h
t/fragments/person.cpp
t/fragments/person.h
t/fragments/test.c
Clang - Perl bindings to the Clang compiler's indexing interface
=head1 SYNOPSIS
use Clang;
my $index = Clang::Index -> new(1);
my $tunit = $index -> parse('file.c');
my $nodes = $tunit -> cursor -> children;
foreach my $node (@$nodes) {
say $node -> spelling;
say $node -> kind -> spelling;
}
=head1 DESCRIPTION
Clang is a compiler front end for the C, C++, Objective-C, and Objective-C++
programming languages which uses LLVM as its back end.
lib/Clang.pm view on Meta::CPAN
version 0.09
=head1 SYNOPSIS
use Clang;
my $index = Clang::Index -> new(1);
my $tunit = $index -> parse('file.c');
my $nodes = $tunit -> cursor -> children;
foreach my $node (@$nodes) {
say $node -> spelling;
say $node -> kind -> spelling;
}
=head1 DESCRIPTION
Clang is a compiler front end for the C, C++, Objective-C, and Objective-C++
programming languages which uses LLVM as its back end.
lib/Clang/Cursor.pm view on Meta::CPAN
package Clang::Cursor;
$Clang::Cursor::VERSION = '0.09';
use strict;
use warnings;
=head1 NAME
Clang::Cursor - Clang cursor class
=head1 VERSION
version 0.09
=head1 DESCRIPTION
A C<Clang::Cursor> represents an element in the abstract syntax tree of a
translation unit.
=head1 METHODS
=head2 kind( )
Retrieve the L<Clang::CursorKind> of the given cursor.
=head2 type( )
Retrieve the L<Clang::Type> of the entity referenced by the given cursor.
=head2 spelling( )
Retrieve the name for the entity referenced by the given cursor.
=head2 num_arguments( )
Retrieve the number of arguments referenced by the given cursor.
=head2 displayname( )
Return the display name for the entity referenced by the given cursor.
=head2 children( )
Retrieve a list of the children of the given cursor. The children are
C<Clang::Cursor> objects too.
=head2 is_pure_virtual( )
Determine whether the given cursor kind represents a pure virtual method.
=head2 is_virtual( )
Determine whether the given cursor kind represents a virtual method.
=head2 location( )
Retrieve the location of the given cursor. This function returns five values: a
string containing the source file name, an integer containing the initial line
number, an integer containing the initial column number, an integer containing
the final line number, and another integer containing the final column number.
=head2 access_specifier( )
Retrieve the access of the given cursor. This can return the following values:
C<invalid>, C<public>, C<protected> or C<private>. Note that this only works
for C++ code, it will return C<invalid> for C functions.
=head1 AUTHOR
Alessandro Ghedini <alexbio@cpan.org>
=head1 LICENSE AND COPYRIGHT
Copyright 2012 Alessandro Ghedini.
lib/Clang/CursorKind.pm view on Meta::CPAN
package Clang::CursorKind;
$Clang::CursorKind::VERSION = '0.09';
use strict;
use warnings;
=head1 NAME
Clang::CursorKind - Clang cursor kind class
=head1 VERSION
version 0.09
=head1 DESCRIPTION
A C<Clang::CursorKind> describes the kind of entity that a cursor refers to.
=head1 METHODS
=head2 spelling( )
Retrieve the name of the given cursor kind.
=head2 is_declaration( )
Determine whether the given cursor kind represents a declaration.
=head2 is_reference( )
Determine whether the given cursor kind represents a reference.
=head2 is_expression( )
Determine whether the given cursor kind represents an expression.
=head2 is_statement( )
Determine whether the given cursor kind represents a statement.
=head2 is_attribute( )
Determine whether the given cursor kind represents an attribute.
=head2 is_invalid( )
Determine whether the given cursor kind represents an invalid cursor.
=head2 is_tunit( )
Determine whether the given cursor kind represents a translation unit.
=head2 is_preprocessing( )
Determine whether the given cursor kind represents a preprocessing element.
=head2 is_unexposed( )
Determine whether the given cursor kind represents an unexposed piece of the
AST.
=head1 AUTHOR
Alessandro Ghedini <alexbio@cpan.org>
=head1 LICENSE AND COPYRIGHT
Copyright 2012 Alessandro Ghedini.
lib/Clang/TUnit.pm view on Meta::CPAN
=head1 VERSION
version 0.09
=head1 DESCRIPTION
A C<Clang::TUnit> represents a single translation unit which resides in an index.
=head1 METHODS
=head2 cursor( )
Retrieve the L<Clang::Cursor> corresponding to the given translation unit.
=head2 spelling( )
Retrieve the original translation unit source file name.
=head2 diagnostics( )
Retrieve the L<Clang::Diagnostic>s associated with the given C<Clang::TUnit>.
t/02-cursor.t view on Meta::CPAN
#!perl -T
use Test::More;
use Clang;
my $index = Clang::Index -> new(0);
my $tunit = $index -> parse('t/fragments/test.c');
my $cursr = $tunit -> cursor;
is($cursr -> spelling, 't/fragments/test.c');
is($cursr -> displayname, 't/fragments/test.c');
my $cursors = $cursr -> children;
my @spellings = map { $_ -> spelling } @$cursors;
my @expected = qw(
foo
main
);
is_deeply(\@spellings, \@expected);
my ($file, $line, $column) = $cursr -> location;
is($file, ''); is($line, 0); is($column, 0);
my @locations = map { join ' ', $_ -> location } @$cursors;
@expected = (
't/fragments/test.c 1 6 5 2',
't/fragments/test.c 7 5 11 2'
);
is_deeply(\@locations, \@expected);
$index = Clang::Index -> new(0);
$tunit = $index -> parse('t/fragments/main.cpp');
$cursr = $tunit -> cursor;
#Testing of method spelling
is($cursr -> spelling, 't/fragments/main.cpp');
#Testing of method num_arguments
my $num_arguments = 0;
_visit_node_arguments($cursr);
sub _visit_node_arguments {
t/02-cursor.t view on Meta::CPAN
my $children = $node->children;
foreach my $child(@$children) {
_visit_node_arguments($child);
}
}
is($num_arguments, 2);
#Testing of method displayname
is($cursr -> displayname, 't/fragments/main.cpp');
$cursors = $cursr -> children;
@spellings = map { $_ -> spelling } @$cursors;
@expected = qw(
Person
main
);
is_deeply(\@spellings, \@expected);
($file, $line, $column) = $cursr -> location;
is($file, ''); is($line, 0); is($column, 0);
@locations = map { join ' ', $_ -> location } @$cursors;
@expected = (
't/fragments/person.h 4 7 13 2',
't/fragments/main.cpp 3 5 5 2'
);
is_deeply(\@locations, \@expected);
$cursors = @$cursors[0] -> children;
@access = map { join ' ', $_ -> access_specifier } @$cursors;
@expected = (
'public',
'public',
'public',
'public',
'private',
'private',
'private'
);
is_deeply(\@access,\@expected);
#Testing if a method is pure virtual or not
$index = Clang::Index -> new(0);
$tunit = $index -> parse('t/fragments/cat.cc');
$cursr = $tunit -> cursor;
$kind = $cursr -> kind;
$cursors = $cursr -> children;
my $check_pure_virtual = 'false';
my $pure_virtual_name = 'undef';
_visit_node($cursr);
sub _visit_node {
my $node = shift;
if($node->is_pure_virtual){
$pure_virtual_name = $node->spelling;
t/02-cursor.t view on Meta::CPAN
_visit_node($child);
}
}
is($check_pure_virtual,'true');
is($pure_virtual_name,'name');
#Testing if a method is virtual or not
$index = Clang::Index -> new(0);
$tunit = $index -> parse('t/fragments/cat.cc');
$cursr = $tunit -> cursor;
$kind = $cursr -> kind;
$cursors = $cursr -> children;
my $check_virtual = 'false';
my $virtual_name = 'undef';
_visit_node_virtual($cursr);
sub _visit_node_virtual {
my $node = shift;
if($node->is_virtual){
$virtual_name = $node->spelling;
t/02-cursor.t view on Meta::CPAN
}
my $children = $node->children;
foreach my $child(@$children) {
_visit_node_virtual($child);
}
}
is($check_virtual,'true');
is($virtual_name,'name');
$tunit = $index -> parse('t/fragments/main.cpp');
$cursr = $tunit -> cursor;
my $method_num_arguments = -4;
_visit_node_method_arguments($cursr);
sub _visit_node_method_arguments {
my $node = shift;
if($node->kind->spelling() eq "CXXMethod"){
if ($node->spelling() eq "walk"){
$method_num_arguments = $node->num_arguments;
is($method_num_arguments, 2);
}
t/02-cursor.t view on Meta::CPAN
is($method_num_arguments, 0);
}
}
my $children = $node->children;
foreach my $child(@$children) {
_visit_node_method_arguments($child);
}
}
$tunit = $index -> parse('t/fragments/test.c');
$cursr = $tunit -> cursor;
my $function_num_arguments = -5;
_visit_node_method_arguments($cursr);
sub _visit_node_method_arguments {
my $node = shift;
if($node->kind->spelling() eq "FunctionDecl"){
if ($node->spelling() eq "foo"){
$method_num_arguments = $node->num_arguments;
is($method_num_arguments, 1);
}
t/03-cursorkind.t view on Meta::CPAN
#!perl -T
use Test::More;
use Clang;
my $index = Clang::Index -> new(0);
my $tunit = $index -> parse('t/fragments/test.c');
my $cursr = $tunit -> cursor;
my $kind = $cursr -> kind;
is($kind -> spelling, 'TranslationUnit');
my $cursors = $cursr -> children;
my @spellings = map { $_ -> kind -> spelling } @$cursors;
my @expected = qw(
FunctionDecl
FunctionDecl
);
is_deeply(\@spellings, \@expected);
done_testing;
t/05-typekind.t view on Meta::CPAN
#!perl -T
use Test::More;
use Clang;
my $index = Clang::Index -> new(0);
my $tunit = $index -> parse('t/fragments/test.c');
my $cursr = $tunit -> cursor;
is($cursr -> type -> kind -> spelling, 'Invalid');
my $cursors = $cursr -> children;
my @spellings = map { $_ -> type -> kind -> spelling } @$cursors;
my @expected = qw(
FunctionProto
FunctionProto
);
is_deeply(\@spellings, \@expected);
done_testing;
t/06-diagnostic.t view on Meta::CPAN
#!perl -T
use Test::More;
use Clang;
my $index = Clang::Index -> new(0);
my $tunit = $index -> parse('t/fragments/test.c');
my $cursr = $tunit -> cursor;
my $diags = $tunit -> diagnostics;
my @formats = map { $_ -> format(1) } @$diags;
my @expected = (
"t/fragments/test.c:2:10: error: use of undeclared identifier 'argp'",
"t/fragments/test.c:4:2: error: void function 'foo' should not return a value",
"t/fragments/test.c:8:6: error: initializing 'int' with an expression of incompatible type 'void'"
);
xs/TUnit.xs view on Meta::CPAN
MODULE = Clang PACKAGE = Clang::TUnit
Cursor
cursor(self)
TUnit self
CODE:
Cursor retval = malloc(sizeof(CXCursor));
CXCursor cursor = clang_getTranslationUnitCursor(self);
*retval = cursor;
RETVAL = retval;
OUTPUT: RETVAL
SV *
spelling(self)
TUnit self
CODE:
CXString spelling = clang_getTranslationUnitSpelling(self);
MODULE = Clang PACKAGE = Clang::Type
Cursor
declaration(self)
Type self
CODE:
Cursor retval = malloc(sizeof(CXCursor));
CXCursor cursor = clang_getTypeDeclaration(*self);
*retval = cursor;
RETVAL = retval;
OUTPUT: RETVAL
TypeKind
kind(self)
Type self
CODE: