This file is indexed.

/usr/share/doc/libnet-ldap-perl/examples/ldifsort.pl is in libnet-ldap-perl 1:0.6500+dfsg-1.

This file is owned by root:root, with mode 0o755.

The actual contents of the file can be viewed below.

  1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
#! /usr/bin/perl
# $Id: ldifsort.pl,v 1.9 2005/04/03 20:20:24 subbarao Exp $

=head1 NAME

ldifsort.pl - Sorts an LDIF file by the specified key attribute. The sorted
version is written to standard output.

=head1 DESCRIPTION

Sorts an LDIF file by the specified key attribute.

=head1 SYNOPSIS

ldifsort.pl B<-k keyattr> [B<-andc>] file.ldif

=over 4

=item B<-k>

Specifies the key attribute for making sort comparisons. If 'dn' is
specified, sorting is done by the full DN string, which can be composed of
different attributes for different entries.

=item B<-a>

Specifies that attributes within a given entry should also be sorted. This
has the side effect of removing all comments and line continuations in the
LDIF file.

=item B<-n>

Specifies numeric comparisons on the key attribute. Otherwise string
comparisons are done.

=item B<-d>

Specifies that the key attribute is a DN. Comparisons are done on a
DN-normalized version of attribute values. This is the default
behavior if 'dn' is passed as the argument to B<-k>.

=item B<-c>

Specifies case-insensitive comparisons on the key attribute. This is the
default behavior if 'dn' is passed as the argument to B<-k>.

=back


=head1 AUTHOR

Kartik Subbarao E<lt>subbarao@computer.orgE<gt>

=cut


use Net::LDAP::Util qw(canonical_dn);
use MIME::Base64;
use Getopt::Std;

use strict;

my %args;
getopts("k:andc", \%args);

my $keyattr = $args{k};
my $sortattrs = $args{a};
my $ciscmp = $args{c};
my $ldiffile = $ARGV[0];

die "usage: $0 -k keyattr [-n] [-d] [-c] ldiffile\n"
	unless $keyattr && $ldiffile;

$/ = "";

open(LDIFH, $ldiffile) || die "$ldiffile: $!\n";

my $pos = 0;
my @valuepos;
while (<LDIFH>) {
	my $value;
	1 while s/^($keyattr:.*)?\n /$1/im; # Handle line continuations
	if (/^$keyattr(::?) (.*)$/im) {
		$value = $2;
		$value = decode_base64($value) if $1 eq '::';
	}
	$value = lc($value) if $ciscmp;
	push @valuepos, [ $value, $pos ];
	$pos = tell;
}

sub cmpattr { $a->[0] cmp $b->[0] }
sub cmpattrnum { $a->[0] <=> $b->[0] }
my %canonicaldns;
sub cmpdn {
	my $cadn = ($canonicaldns{$a->[0]} ||= lc(canonical_dn($a->[0])));
	my $cbdn = ($canonicaldns{$b->[0]} ||= lc(canonical_dn($b->[0])));
	$cadn cmp $cbdn;
}

my $cmpfunc;
if ($args{d} || lc($keyattr) eq 'dn') { $cmpfunc = \&cmpdn }
elsif ($args{n}) { $cmpfunc = \&cmpattrnum }
else { $cmpfunc = \&cmpattr; }

my @sorted;
@sorted = sort $cmpfunc @valuepos;

foreach my $valuepos (@sorted) {
	seek(LDIFH, $valuepos->[1], 0);
	my $entry = <LDIFH>;
	if ($sortattrs) {
		$entry =~ s/\n //mg; # collapse line continuations
		my @lines = grep(!/^#/, split(/\n/, $entry));
		my $dn = shift(@lines);
		print "$dn\n", join("\n", sort @lines), "\n\n";
	}
	else {
		print $entry;
		print "\n" if $entry !~ /\n\n$/;
	}
}