]> git.sur5r.net Git - openldap/blob - servers/slapd/shell-backends/passwd-shell.c
Fix wait4child change: Prefer wait3 over wait. Use SIGNAL instead of signal.
[openldap] / servers / slapd / shell-backends / passwd-shell.c
1 /*
2  passwd-shell.c - /etc/passwd shell-based backend for standalone ldap server
3
4  Copyright (c) 1995 Regents of the University of Michigan.
5  All rights reserved.
6
7  Redistribution and use in source and binary forms are permitted
8  provided that this notice is preserved and that due credit is given
9  to the University of Michigan at Ann Arbor. The name of the University
10  may not be used to endorse or promote products derived from this
11  software without specific prior written permission. This software
12  is provided ``as is'' without express or implied warranty.
13 */
14
15
16 #include "portable.h"
17
18 #include <stdio.h>
19 #include <stdlib.h>
20
21 #include <ac/string.h>
22 #include <ac/unistd.h>
23
24 #include <pwd.h>
25
26 #include <lber.h>
27 #include <ldap.h>
28
29 #include "shellutil.h"
30 #include "passwd-shell.h"
31
32
33 static void pwdfile_search LDAP_P(( struct ldop *op, FILE *ofp ));
34 static struct ldentry *pw2entry LDAP_P(( struct ldop *op, struct passwd *pw ));
35
36 static char     tmpbuf[ MAXLINELEN * 2 ];
37
38
39 int
40 main( int argc, char **argv )
41 {
42     int                 c, errflg;
43     struct ldop         op;
44
45     if (( progname = strrchr( argv[ 0 ], '/' )) == NULL ) {
46         progname = estrdup( argv[ 0 ] );
47     } else {
48         progname = estrdup( progname + 1 );
49     }
50
51     errflg = debugflg = 0;
52
53     while (( c = getopt( argc, argv, "d" )) != EOF ) {
54         switch( c ) {
55         case 'd':
56 #ifdef LDAP_DEBUG
57             ++debugflg;
58 #else /* LDAP_DEBUG */
59             fprintf( stderr, "%s: compile with -DLDAP_DEBUG for debugging\n",
60                     progname );
61 #endif /* LDAP_DEBUG */
62             break;
63         default:
64             ++errflg;
65         }
66     }
67
68     if ( errflg || optind < argc ) {
69         fprintf( stderr, "usage: %s [-d]\n", progname );
70         exit( 1 );
71     }
72
73     debug_printf( "started\n" );
74
75     (void) memset( (char *)&op, '\0', sizeof( op ));
76
77     if ( parse_input( stdin, stdout, &op ) < 0 ) {
78         exit( 0 );
79     }
80
81     if ( op.ldop_op != LDOP_SEARCH ) {
82         write_result( stdout, LDAP_UNWILLING_TO_PERFORM, NULL,
83                 "Command Not Implemented" );
84         exit( 0 );
85     }
86
87 #ifdef LDAP_DEBUG
88     dump_ldop( &op );
89 #endif /* LDAP_DEBUG */
90
91     pwdfile_search( &op, stdout );
92
93     exit( 0 );
94 }
95
96
97 static void
98 pwdfile_search( struct ldop *op, FILE *ofp )
99 {
100     struct passwd       *pw;
101     struct ldentry      *entry;
102     int                 oneentry;
103
104     oneentry = ( strchr( op->ldop_dn, '@' ) != NULL );
105
106     for ( pw = getpwent(); pw != NULL; pw = getpwent()) {
107         if (( entry = pw2entry( op, pw )) != NULL ) {
108             if ( oneentry ) {
109                 if ( dn_casecmp( op->ldop_dn, entry->lde_dn ) == 0 ) {
110                     write_entry( op, entry, ofp );
111                     break;
112                 }
113             } else if ( test_filter( op, entry )) {
114                 write_entry( op, entry, ofp );
115             }
116             free_entry( entry );
117         }
118     }
119     endpwent();
120
121     write_result( ofp, LDAP_SUCCESS, NULL, NULL );
122 }
123
124
125 static struct ldentry *
126 pw2entry( struct ldop *op, struct passwd *pw )
127 {
128     struct ldentry      *entry;
129     struct ldattr       *attr;
130     int                 i;
131
132     entry = (struct ldentry *) ecalloc( 1, sizeof( struct ldentry ));
133
134     /* 
135      * construct the DN from pw_name
136      */
137     if ( strchr( op->ldop_suffixes[ 0 ], '=' ) != NULL ) {
138         /*
139          * X.500 style DN
140          */
141         sprintf( tmpbuf, "cn=%s, %s", pw->pw_name, op->ldop_suffixes[ 0 ] );
142     } else {
143         /*
144          * RFC-822 style DN
145          */
146         sprintf( tmpbuf, "%s@%s", pw->pw_name, op->ldop_suffixes[ 0 ] );
147     }
148     entry->lde_dn = estrdup( tmpbuf );
149
150     /*
151      * for now, we simply derive the LDAP attribute values as follows:
152      *  objectClass = person
153      *  uid = pw_name
154      *  sn = pw_name
155      *  cn = pw_name
156      *  cn = pw_gecos   (second common name)
157      */
158     entry->lde_attrs = (struct ldattr **)ecalloc( 5, sizeof( struct ldattr * ));
159     i = 0;
160     attr = (struct ldattr *)ecalloc( 1, sizeof( struct ldattr ));
161     attr->lda_name = estrdup( "objectClass" );
162     attr->lda_values = (char **)ecalloc( 2, sizeof( char * ));
163     attr->lda_values[ 0 ] = estrdup( "person" );
164     entry->lde_attrs[ i++ ] = attr;
165
166     attr = (struct ldattr *)ecalloc( 1, sizeof( struct ldattr ));
167     attr->lda_name = estrdup( "uid" );
168     attr->lda_values = (char **)ecalloc( 2, sizeof( char * ));
169     attr->lda_values[ 0 ] = estrdup( pw->pw_name );
170     entry->lde_attrs[ i++ ] = attr;
171
172     attr = (struct ldattr *)ecalloc( 1, sizeof( struct ldattr ));
173     attr->lda_name = estrdup( "sn" );
174     attr->lda_values = (char **)ecalloc( 2, sizeof( char * ));
175     attr->lda_values[ 0 ] = estrdup( pw->pw_name );
176     entry->lde_attrs[ i++ ] = attr;
177
178     attr = (struct ldattr *)ecalloc( 1, sizeof( struct ldattr ));
179     attr->lda_name = estrdup( "cn" );
180     attr->lda_values = (char **)ecalloc( 3, sizeof( char * ));
181     attr->lda_values[ 0 ] = estrdup( pw->pw_name );
182     if ( pw->pw_gecos != NULL && *pw->pw_gecos != '\0' ) {
183         attr->lda_values[ 1 ] = estrdup( pw->pw_gecos );
184     }
185     entry->lde_attrs[ i++ ] = attr;
186
187     return( entry );
188 }