]> git.sur5r.net Git - openldap/blob - servers/ldapd/message.c
schema definitions from Active Directory.
[openldap] / servers / ldapd / message.c
1 /* $OpenLDAP$ */
2 /*
3  * Copyright (c) 1990 Regents of the University of Michigan.
4  * All rights reserved.
5  *
6  * Redistribution and use in source and binary forms are permitted
7  * provided that this notice is preserved and that due credit is given
8  * to the University of Michigan at Ann Arbor. The name of the University
9  * may not be used to endorse or promote products derived from this
10  * software without specific prior written permission. This software
11  * is provided ``as is'' without express or implied warranty.
12  */
13
14 #include "portable.h"
15
16 #include <stdio.h>
17
18 #include <ac/socket.h>
19 #include <ac/string.h>
20
21 #include <quipu/commonarg.h>
22 #include <quipu/ds_error.h>
23
24 #include "lber.h"
25 #include "ldap.h"
26 #include "common.h"
27
28 static struct msg       *messages;
29
30 struct msg *add_msg(
31     int                 msgid,
32     int                 msgtype,
33     BerElement          *ber,
34     struct conn         *dsaconn,
35     int                 udp,
36     struct sockaddr     *clientaddr
37 )
38 {
39         struct msg              *new;
40         static int              uniqid = 0;
41
42         /* make a new message */
43         if ( (new = (struct msg *) malloc( sizeof(struct msg) )) == NULL ) {
44                 Debug( LDAP_DEBUG_ANY, "addmsg: malloc failed\n", 0, 0, 0 );
45                 return( NULL );
46         }
47         new->m_msgid = msgid;
48         new->m_uniqid = ++uniqid;
49         new->m_msgtype = msgtype;
50         new->m_ber = ber;
51         new->m_mods = NULL;
52         new->m_conn = dsaconn;
53         new->m_conn->c_refcnt++;
54         new->m_next = NULL;
55
56 #ifdef LDAP_CONNECTIONLESS
57         new->m_cldap = udp;
58         new->m_searchbase = NULLDN;
59
60         if ( udp ) {
61                 new->m_clientaddr = *clientaddr;
62                 Debug( LDAP_DEBUG_TRACE, "udp message from %s port %d\n", 
63                     inet_ntoa( ((struct sockaddr_in *)clientaddr)->sin_addr ),
64                     ((struct sockaddr_in *)clientaddr)->sin_port, 0 );
65         }
66 #endif
67
68         /* add it to the front of the queue */
69         new->m_next = messages;
70         messages = new;
71
72         return( new );
73 }
74
75 struct msg *get_msg( int uniqid )
76 {
77         struct msg      *tmp;
78
79         for ( tmp = messages; tmp != NULL; tmp = tmp->m_next ) {
80                 if ( tmp->m_uniqid == uniqid )
81                         return( tmp );
82         }
83
84         return( NULL );
85 }
86
87 int
88 del_msg( struct msg *m )
89 {
90         struct msg      *cur, *prev;
91
92         prev = NULL;
93         for ( cur = messages; cur != NULL; cur = cur->m_next ) {
94                 if ( cur == m )
95                         break;
96                 prev = cur;
97         }
98
99         if ( cur == NULL ) {
100                 Debug( LDAP_DEBUG_ANY, "delmsg: cannot find msg %lx\n",
101                        (unsigned long) m, 0, 0 );
102                 return( -1 );
103         }
104
105         if ( prev == NULL ) {
106                 messages = cur->m_next;
107         } else {
108                 prev->m_next = cur->m_next;
109         }
110         conn_free( cur->m_conn );
111         modlist_free( cur->m_mods );
112         ber_free( cur->m_ber, 1 );
113 #ifdef LDAP_CONNECTIONLESS
114         if ( cur->m_searchbase != NULLDN ) {
115             dn_free( cur->m_searchbase );
116         }
117 #endif /* LDAP_CONNECTIONLESS */
118         free( (char *) cur );
119
120         return( 0 );
121 }
122
123 /*
124  * send_msg - Send a messge in response to every outstanding request on
125  * a given connection.  This is used, for example, when an association to
126  * a dsa fails.  It deletes messages to which it responds.
127  */
128
129 void
130 send_msg(
131     struct conn *conn,
132     Sockbuf     *clientsb,
133     int         err,
134     char        *str
135 )
136 {
137         struct msg      *tmp, *next;
138
139         next = NULL;
140         for ( tmp = messages; tmp != NULL; tmp = next ) {
141                 next = tmp->m_next;
142
143                 if ( tmp->m_conn == conn ) {
144                         send_ldap_msgresult( clientsb, tmp->m_msgtype, tmp,
145                             err, NULL, str );
146                 }
147
148                 del_msg( tmp );
149         }
150 }
151
152
153 #ifdef LDAP_CONNECTIONLESS
154 struct msg *
155 get_cldap_msg(
156     int                 msgid,
157     int                 msgtype,
158     struct sockaddr     *fromaddr
159 )
160 {
161         struct msg      *tmp;
162
163         for ( tmp = messages; tmp != NULL; tmp = tmp->m_next ) {
164                 if ( tmp->m_cldap && tmp->m_msgid == msgid &&
165                     tmp->m_msgtype == msgtype &&
166                     ((struct sockaddr_in *)&tmp->m_clientaddr)->sin_port ==
167                     ((struct sockaddr_in *)fromaddr)->sin_port &&
168                     ((struct sockaddr_in *)&tmp->m_clientaddr)->sin_addr
169                     == ((struct sockaddr_in *)fromaddr)->sin_addr ) {
170                         break;
171                 }
172         }
173
174         return( tmp );
175 }
176 #endif /* LDAP_CONNECTIONLESS */