00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021 #include "ber.h"
00022 #include "kldap_config.h"
00023
00024 #include <kdebug.h>
00025
00026 #include <QtCore/QList>
00027 #include <qvarlengtharray.h>
00028
00029 #include <cstdarg>
00030
00031 #ifdef LDAP_FOUND
00032
00033 #ifdef Q_OS_SOLARIS //krazy:exclude=cpp
00034 #define BC31 1
00035 #endif
00036
00037 #ifndef HAVE_WINLDAP_H
00038 #include <lber.h>
00039 #include <ldap.h>
00040 #else
00041 #include <w32-ldap-help.h>
00042 #endif
00043
00044 #ifndef LBER_USE_DER
00045 #define LBER_USE_DER 1
00046 #endif
00047
00048 #ifndef HAVE_BER_MEMFREE
00049 # ifndef HAVE_WINLDAP_H
00050 # define ber_memfree(x) ldap_memfree(x)
00051 # else
00052 # define ber_memfree(x) win_ldap_memfree(x)
00053 # endif
00054 #endif
00055
00056 #endif
00057
00058 using namespace KLDAP;
00059
00060 class Ber::BerPrivate
00061 {
00062 public:
00063 #ifdef LDAP_FOUND
00064 BerElement *mBer;
00065 #endif
00066 };
00067
00068 #ifdef LDAP_FOUND
00069 Ber::Ber()
00070 : d( new BerPrivate )
00071 {
00072 d->mBer = ber_alloc_t( LBER_USE_DER );
00073 Q_ASSERT( d->mBer );
00074 }
00075
00076 Ber::Ber( const QByteArray &value )
00077 : d( new BerPrivate )
00078 {
00079 struct berval bv;
00080 bv.bv_val = (char*) value.data();
00081 bv.bv_len = value.size();
00082 d->mBer = ber_init( &bv );
00083 Q_ASSERT( d->mBer );
00084 }
00085
00086 Ber::~Ber()
00087 {
00088 ber_free( d->mBer, 1 );
00089 delete d;
00090 }
00091
00092 Ber::Ber( const Ber &that )
00093 : d( new BerPrivate )
00094 {
00095 struct berval *bv;
00096 if ( ber_flatten( that.d->mBer, &bv ) == 0 ) {
00097 d->mBer = ber_init( bv );
00098 ber_bvfree( bv );
00099 }
00100 }
00101
00102 Ber &Ber::operator=( const Ber &that )
00103 {
00104 if ( this == &that ) {
00105 return *this;
00106 }
00107
00108 struct berval *bv;
00109 if ( ber_flatten( that.d->mBer, &bv ) == 0 ) {
00110 d->mBer = ber_init( bv );
00111 ber_bvfree( bv );
00112 }
00113 return *this;
00114 }
00115
00116 QByteArray Ber::flatten() const
00117 {
00118 QByteArray ret;
00119 struct berval *bv;
00120 if ( ber_flatten( d->mBer, &bv ) == 0 ) {
00121 ret = QByteArray( bv->bv_val, bv->bv_len );
00122 ber_bvfree( bv );
00123 }
00124 return ret;
00125 }
00126
00127 int Ber::printf( const QString &format, ... )
00128 {
00129 char fmt[2];
00130 va_list args;
00131 va_start ( args, format );
00132 fmt[1] = '\0';
00133
00134 int i = 0, ret = 0;
00135 while ( i < format.length() ) {
00136 fmt[0] = format[i].toLatin1();
00137 i++;
00138 switch ( fmt[0] ) {
00139 case 'b':
00140 case 'e':
00141 case 'i':
00142 {
00143 ber_int_t v = va_arg( args, int );
00144 ret = ber_printf( d->mBer, fmt, v );
00145 break;
00146 }
00147 case 'B':
00148 {
00149
00150 QByteArray *B = va_arg( args, QByteArray * );
00151 int Bc = va_arg( args, int );
00152 ret = ber_printf( d->mBer, fmt, B->data(), Bc );
00153 break;
00154 }
00155 case 'o':
00156 {
00157 QByteArray *o = va_arg( args, QByteArray * );
00158 ret = ber_printf( d->mBer, fmt, o->data(), o->size() );
00159 break;
00160 }
00161 case 'O':
00162 {
00163 QByteArray *O = va_arg( args, QByteArray * );
00164 struct berval bv;
00165 bv.bv_val = (char*) O->data();
00166 bv.bv_len = O->size();
00167 ret = ber_printf( d->mBer, fmt, &bv );
00168 break;
00169 }
00170 break;
00171 case 's':
00172 {
00173 QByteArray *s = va_arg( args, QByteArray * );
00174 ret = ber_printf( d->mBer, fmt, s->data() );
00175 break;
00176 }
00177 break;
00178 case 't':
00179 {
00180 unsigned int t = va_arg( args, unsigned int );
00181 ret = ber_printf( d->mBer, fmt, t );
00182 break;
00183 }
00184 break;
00185 case 'v':
00186 {
00187 QList<QByteArray> *v = va_arg( args, QList<QByteArray> * );
00188 QVarLengthArray<const char *> l( v->count()+1 );
00189 int j;
00190 for ( j = 0; j < v->count(); j++ ) {
00191 l[j] = v->at(j).data();
00192 }
00193 l[j] = 0;
00194 ret = ber_printf( d->mBer, fmt, l.data() );
00195 break;
00196 }
00197 case 'V':
00198 {
00199 QList<QByteArray> *V = va_arg( args, QList<QByteArray> * );
00200 QVarLengthArray<struct berval *> bv ( V->count()+1 );
00201 QVarLengthArray<struct berval> bvs( V->count( ) );
00202 int j;
00203 for ( j = 0; j < V->count(); j++ ) {
00204 bvs[j].bv_val = (char *) V->at(j).data();
00205 bvs[j].bv_len = V->at(j).size();
00206 bv[j] = &bvs[j];
00207 }
00208 bv[V->count()] = 0;
00209 ret = ber_printf( d->mBer, fmt, bv.data() );
00210 break;
00211 }
00212 case 'n':
00213 case '{':
00214 case '}':
00215 case '[':
00216 case ']':
00217 ret = ber_printf( d->mBer, fmt );
00218 break;
00219 default:
00220 kWarning() << "Invalid BER format parameter: '" << fmt << "'";
00221 ret = -1;
00222 }
00223 kDebug() << "ber_printf format:" << fmt << "ret:" << ret;
00224 if ( ret == -1 ) {
00225 break;
00226 }
00227 }
00228 va_end( args );
00229 return ret;
00230 }
00231
00232 int Ber::scanf( const QString &format, ... )
00233 {
00234 char fmt[2];
00235 va_list args;
00236 va_start ( args, format );
00237 fmt[1] = '\0';
00238
00239 int i = 0, ret = 0;
00240 while ( i < format.length() ) {
00241 fmt[0] = format[i].toLatin1();
00242 i++;
00243 switch ( fmt[0] ) {
00244 case 'l':
00245 case 'b':
00246 case 'e':
00247 case 'i':
00248 {
00249 int *v = va_arg( args, int * );
00250 ret = ber_scanf( d->mBer, fmt, v );
00251 break;
00252 }
00253 case 'B':
00254 {
00255
00256 QByteArray *B = va_arg( args, QByteArray * );
00257 int *Bc = va_arg( args, int * );
00258 char *c;
00259 ret = ber_scanf( d->mBer, fmt, &c, Bc );
00260 if ( ret != -1 ) {
00261 *B = QByteArray( c, ( *Bc + 7 ) / 8 );
00262 ber_memfree( c );
00263 }
00264 break;
00265 }
00266 case 'o':
00267 {
00268 QByteArray *o = va_arg( args, QByteArray * );
00269 struct berval bv;
00270 ret = ber_scanf( d->mBer, fmt, &bv );
00271 if ( ret != -1 ) {
00272 *o = QByteArray( bv.bv_val, bv.bv_len );
00273 ber_memfree( bv.bv_val );
00274 }
00275 break;
00276 }
00277 case 'O':
00278 {
00279 QByteArray *O = va_arg( args, QByteArray * );
00280 struct berval *bv;
00281 ret = ber_scanf( d->mBer, fmt, &bv );
00282 if ( ret != -1 ) {
00283 *O = QByteArray( bv->bv_val, bv->bv_len );
00284 ber_bvfree( bv );
00285 }
00286 break;
00287 }
00288 break;
00289 case 'm':
00290 {
00291 QByteArray *m = va_arg( args, QByteArray * );
00292 struct berval *bv;
00293 ret = ber_scanf( d->mBer, fmt, &bv );
00294 if ( ret != -1 ) {
00295 *m = QByteArray( bv->bv_val, bv->bv_len );
00296 }
00297 break;
00298 }
00299 case 'a':
00300 {
00301 QByteArray *a = va_arg( args, QByteArray * );
00302 char *c;
00303 ret = ber_scanf( d->mBer, fmt, &c );
00304 if ( ret != -1 ) {
00305 *a = QByteArray( c );
00306 ber_memfree( c );
00307 }
00308 break;
00309 }
00310
00311 case 's':
00312 {
00313 QByteArray *s = va_arg( args, QByteArray * );
00314 char buf[255];
00315 ber_len_t l = sizeof( buf );
00316 ret = ber_scanf( d->mBer, fmt, &buf, &l );
00317 if ( ret != -1 ) {
00318 *s = QByteArray( buf, l );
00319 }
00320 break;
00321 }
00322 case 't':
00323 case 'T':
00324 {
00325 unsigned int *t = va_arg( args, unsigned int * );
00326 ret = ber_scanf( d->mBer, fmt, t );
00327 break;
00328 }
00329 break;
00330 case 'v':
00331 {
00332 QList<QByteArray> *v = va_arg( args, QList<QByteArray> * );
00333 char **c, **c2;
00334 ret = ber_scanf( d->mBer, fmt, &c );
00335 if ( ret != -1 && c ) {
00336 c2 = c;
00337 while ( *c ) {
00338 v->append( QByteArray( *c ) );
00339 ber_memfree( *c );
00340 c++;
00341 }
00342 ber_memfree( (char *) c2 );
00343 }
00344 break;
00345 }
00346 case 'V':
00347 {
00348 QList<QByteArray> *v = va_arg( args, QList<QByteArray> * );
00349 struct berval **bv, **bv2;
00350 ret = ber_scanf( d->mBer, fmt, &bv );
00351 if ( ret != -1 && bv ) {
00352 bv2 = bv;
00353 while ( *bv ) {
00354 v->append( QByteArray( (*bv)->bv_val, (*bv)->bv_len ) );
00355 bv++;
00356 }
00357 ber_bvecfree( bv2 );
00358 }
00359 break;
00360 }
00361 case 'x':
00362 case 'n':
00363 case '{':
00364 case '}':
00365 case '[':
00366 case ']':
00367 ret = ber_scanf( d->mBer, fmt );
00368 break;
00369 default:
00370 kWarning() << "Invalid BER format parameter: '" << fmt << "'";
00371 ret = -1;
00372 }
00373
00374 kDebug() << "ber_scanf format:" << fmt << "ret:" << ret;
00375 if ( ret == -1 ) {
00376 break;
00377 }
00378
00379 }
00380 va_end( args );
00381 return ret;
00382 }
00383
00384 unsigned int Ber::peekTag( int &size )
00385 {
00386 unsigned int ret;
00387 ber_len_t len;
00388 ret = ber_peek_tag( d->mBer, &len );
00389 size = len;
00390 return ret;
00391 }
00392
00393 unsigned int Ber::skipTag( int &size )
00394 {
00395 unsigned int ret;
00396 ber_len_t len;
00397 ret = ber_skip_tag( d->mBer, &len );
00398 size = len;
00399 return ret;
00400 }
00401 #else
00402
00403 Ber::Ber()
00404 : d( new BerPrivate )
00405 {
00406 kError() << "LDAP support not compiled";
00407 }
00408
00409 Ber::Ber( const QByteArray & )
00410 : d( new BerPrivate )
00411 {
00412 kError() << "LDAP support not compiled";
00413 }
00414
00415 Ber::~Ber()
00416 {
00417 delete d;
00418 }
00419
00420 Ber::Ber( const Ber & )
00421 : d( new BerPrivate )
00422 {
00423 kError() << "LDAP support not compiled";
00424 }
00425
00426 Ber &Ber::operator=( const Ber &that )
00427 {
00428 if ( this == &that ) {
00429 return *this;
00430 }
00431 kError() << "LDAP support not compiled";
00432 return *this;
00433 }
00434
00435 QByteArray Ber::flatten() const
00436 {
00437 kError() << "LDAP support not compiled";
00438 return QByteArray();
00439 }
00440
00441 int Ber::printf( const QString &format, ... )
00442 {
00443 Q_UNUSED( format );
00444 kError() << "LDAP support not compiled";
00445 return -1;
00446 }
00447
00448 int Ber::scanf( const QString &format, ... )
00449 {
00450 Q_UNUSED( format );
00451 kError() << "LDAP support not compiled";
00452 return -1;
00453 }
00454
00455 unsigned int Ber::peekTag( int &size )
00456 {
00457 Q_UNUSED( size );
00458 kError() << "LDAP support not compiled";
00459 return 0;
00460 }
00461
00462 unsigned int Ber::skipTag( int &size )
00463 {
00464 Q_UNUSED( size );
00465 kError() << "LDAP support not compiled";
00466 return 0;
00467 }
00468
00469 #endif