This file is indexed.

/usr/include/ptclib/podbc.h is in libpt-dev 2.10.11~dfsg-1ubuntu1.

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

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
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
654
655
656
657
658
659
660
661
662
663
664
665
666
667
668
669
670
671
672
673
674
675
676
677
678
679
680
681
682
683
684
685
686
687
688
689
690
691
692
693
694
695
696
697
698
699
700
701
702
703
704
705
706
707
708
709
710
711
712
713
714
715
716
717
718
719
720
721
722
723
724
725
726
727
728
729
730
731
732
733
734
735
736
737
738
739
740
741
742
743
744
745
746
747
748
749
750
751
752
753
754
755
756
757
758
759
760
761
762
763
764
765
766
767
768
769
770
771
772
773
774
775
776
777
778
779
780
781
782
783
784
785
786
787
788
789
790
791
792
793
794
795
796
797
798
799
800
801
802
803
804
805
806
807
808
809
810
811
812
813
814
815
816
817
818
819
820
821
822
823
824
825
826
827
828
829
830
831
832
833
834
835
836
837
838
839
840
841
842
843
844
845
846
847
848
849
850
851
852
853
854
855
856
857
858
859
860
861
862
863
864
865
866
867
868
869
870
871
872
873
874
875
876
877
878
879
880
881
882
883
884
885
886
887
888
889
890
891
892
893
894
895
896
897
898
899
900
901
902
903
904
905
906
907
908
909
910
911
912
913
914
915
916
917
918
919
920
921
922
923
924
925
926
927
928
929
930
931
932
933
934
935
936
937
938
939
940
941
942
943
944
945
946
/*
 * podbc.h
 *
 * Virteos ODBC Implementation for PWLib Library.
 *
 * Virteos is a Trade Mark of ISVO (Asia) Pte Ltd.
 *
 * Copyright (c) 2005 ISVO (Asia) Pte Ltd. All Rights Reserved.
 *
 * The contents of this file are subject to the Mozilla Public License
 * Version 1.0 (the "License"); you may not use this file except in
 * compliance with the License. You may obtain a copy of the License at
 * http://www.mozilla.org/MPL/
 *
 * Software distributed under the License is distributed on an "AS IS"
 * basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
 * the License for the specific language governing rights and limitations
 * under the License.
 *
 *
 * The Original Code is derived from and used in conjunction with the 
 * pwlib Libaray of the OpenH323 Project (www.openh323.org/)
 *
 * The Initial Developer of the Original Code is ISVO (Asia) Pte Ltd.
 *
 *   Portions: Simple ODBC Wrapper Article www.codeproject.com
 *
 * Contributor(s): ______________________________________.
 *
 * $Revision: 24177 $
 * $Author: rjongbloed $
 * $Date: 2010-04-05 06:52:04 -0500 (Mon, 05 Apr 2010) $
 */

/**
  ODBC Support for PWLIB

  Class Description
   PODBC        :  Main DataBase Connection Class (Derive Class for Error Handling)
   PODBC::ConnectData :  Class used to store information for Connecting to DataSource
   PODBC::Table    :  Retrieved Data Structure (RecordSet) from Table or Select SQL Query
   PODBC::Row      :  Record Pointer Class for the PODBC::Table (PArray of Fields)
   PODBC::Field    :  Database Field Information (Field Structure & Data(Bound))
   PODBC::Field:Bind  :  DataTypes Bound to the RecordSet (change with Record Navigation)
   PDSNConnection    :  Derived Class of PODBC for ODBC Configured Connections
   PODBCStmt      :  Wrapper for RecordSet (Internal)
   PODBCRecord    :  Handle Retrieve/Post/Bind Data from RecordSet (Internal)

  Example of Use

<pre><code>
  PODBC link;
  PODBC::ConnectData data;
  data.DBPath = "test.mdb";

  if (link.DataSource(PODBC::MSAccess,data)) {
    // Load a Database Table (could also be a SELECT Query)
      PODBC::Table table(&link,"FooTable");
  // Bind to Column 1 
      PODBC::Field & field = table.Column(1):
    // Display Contents
      cout << " Value " << field.AsString(); << endl;
  // Move to Record 2 of fooTable
      table[2];  
  // Display contents of Record 2 Column 1
      cout << " Value " << field.AsString(); << endl;
  // Set New Value for Record 2 Field 1 of FooTable
      field.SetValue("NewValue");
  // Send Update to Database.
      field.Post();

    // To Add New Record.(with Default Values)
      table.NewRow();
  // Alter the Value of field 1
      field.SetValue("Somethng");
  // Post the New Field to the Database
      field.Post();

    // Run General Query;
      PString SQLStmt = "INSERT foo into [FooTable] ..."
    Link.Query(SQLStmt);
  }
// Disconnect from ODBC Source
  link.Disconnect();

</code></pre>
*/
//--

#ifndef PTLIB_PODBC_H
#define PTLIB_PODBC_H

#if _MSC_VER > 1000
#pragma once
#endif // _MSC_VER > 1000


#if defined(P_ODBC) && !defined(_WIN32_WCE)

#include <odbcinst.h>
#include <sql.h> 
#include <sqlext.h>

#ifdef _MSC_VER
 #include <tchar.h>
 #pragma comment(lib,"odbc32.lib")
 #pragma comment(lib,"odbcCP32.lib")
#else

  #ifdef UNICODE
  typedef WCHAR                 TCHAR;
  typedef LPWSTR                LPTSTR;
  typedef LPCWSTR               LPCTSTR;
  // Needs a definition one day ... #define _T(x)
  #else
  typedef CHAR                  TCHAR;
  typedef LPSTR                 LPTSTR;
  typedef LPCSTR                LPCTSTR;
  #define _T(x) x
  #endif

#endif // _MSC_VER

// Max SQL String Data Length
#define MAX_DATA_LEN 1024

/** PODBC Statement Class 
  This class is use to parse store queries and Fetch data
  It is not designed to process the actual data only access it.
  PODBC::Record is used to Bind/Retrieve/Store Data Elements. .
*/


class PODBC;
class PODBCRecord;


class PODBCStmt : public PObject
{
    PCLASSINFO(PODBCStmt, PObject);

  public:
    /**@name Constructor/Deconstructor */
    //@{
    /** Constructor PODBC (Datasources call) or thro' DSNConnection (Connection call). 
    In General this class is constructed within the PODBC::Table Class.
    */
    PODBCStmt(PODBC * odbc);

    /** Deconstructor. This Class should be available for the duration of which
    a specific query/table is required and be deconstructed at the time of
    the PODBC::Table deconstruction.
    */
    ~PODBCStmt();
    //@}

    /**@name Handles */
    //@{  
    /** Statement Handle Created by the Query Function.
    */
    operator HSTMT() { return m_hStmt; };
    //@}


    /**@name Data Management */
    //@{ 
    /** IsValid Checks to ensure a Handle has been allocated and
    is effective.
    */
    PBoolean IsValid();

    /** GetChangedRowCount retreives the number of rows updated/altered by
    UPDATE/INSERT statements.
    */
    DWORD GetChangedRowCount(void);

    /** Query function is the Main function to pass SQL statements to retreive/
    add/Modify database data. It accepts generally acceptable SQL Statements.
    ie. Select * from [table-x]
    */
    PBoolean Query(PString strSQL);
    //@}

    /**@name Data Retrieval */
    //@{  
    /** Fetch General call to retreive the next row of data. 
    */
    PBoolean Fetch();

    /** FetchRow More detailed fetching of Rows. This allows you to fetch an
    Absolute row or a row relative to the current row fetched.
    */
    PBoolean FetchRow(PINDEX nRow,PBoolean Absolute=1);

    /** FetchPrevious Fetch the previous Row from current row.
    */
    PBoolean FetchPrevious();

    /** FetchNext: Fetch the Next row. 
    */
    PBoolean FetchNext();

    /** FetchFirst Fetch the First row in the RecordSet 
    */
    PBoolean FetchFirst();

    /** FetchLast Fetch the Last row in the RecordSet
    */
    PBoolean FetchLast();

    /** Cancel the Current Statement
    */
    PBoolean Cancel();
    //@}

    /**@name Utilities */
    //@{ 
    /** Retreive the List of Tables from the current Datasource
    The option field can be used to specify the Table Types
    ie "TABLE" for Tables or "VIEW" for preconfigured datasource
    queries. *Further investigation is required*
    */
    PStringArray TableList(PString option = "");


    /** Is the SQL Instruction OK
    If an Error is detected then GetLastError is called
    to Retrieve the SQL Error Information and Returns false
    */
    PBoolean SQL_OK(SQLRETURN res);

    /** Get the Last Error 
    This returns the Error ID & String to PODBC::OnSQLError
    */
    void GetLastError();

    PODBC * GetLink() const { return odbclink; }
    int GetDBase() const { return dbase; }
    //@}

  protected:
    HSTMT   m_hStmt;
    PODBC * odbclink; /// Reference to the PODBC Class
    int     dbase;    /// Database Type connecting to
};



/** PODBC Class
  The Main ODBC class. This Class should be used in the there is 
  not a preconfigured DSN setup in the MDAC. This class will use
  the applicable ODBC drivers to connect to a compliant Datasource.
  It Supports a wide variety of Datasources but others can added 
  by simply creating your custom connection string and then calling
  PODBC::Connect. For Defined sources the PODBC::DataSource function
  should be used.
*/

class PODBC  : public PObject
{
    PCLASSINFO(PODBC, PObject);

  public:
    /**@name Constructor/Deconstructor */
    //@{
    /** Constructor
    */
    PODBC();

    /** Deconstructor
    */
    ~PODBC();
    //@}

    /**@name Enumerators */
    //@{
    /** Raw SQL data type codes Refer <sql.h> SQL_*
    This list is not inclusive. If an item 
    is not listed or Unknown it is treated 
    as a character string.

    */
    enum FieldTypes
    {
      LongVarChar   =-1,   
      Binary        =-2,
      VarBinary     =-3,
      LongVarBinary =-4,
      BigInt        =-5,
      TinyInt       =-6,
      Bit           =-7,   /// Boolean
      Guid          =-11,
      Unknown       = 0,
      Char          = 1,
      Numeric       = 2,
      Decimal       = 3,
      Integer       = 4,
      SmallInt      = 5,
      Float         = 6,
      Real          = 7,
      Double        = 8,
      DateTime      = 9,
      VarChar       =12,    
      Date          =91,    /// Structure   
      Time          =92,    /// Structure
      TimeStamp     =93     /// Structure  PTime    
    };

    /** Converted Pwlib Field Types.  
    Data is stored as a PString
    and the pwType enumerator indicates
    the conversion required on the PODBC::Field.
    */
    enum PwType
    { 
      oPString,   // String Value
      oBOOL,      // Boolean 
      ochar,      // Character
      oshort,     // Short  
      oint,       // Integer  use .AsInteger()
      olong,      // long    
      odouble,    // Double   use .AsReal()
      oPBYTEArray,// Binary Data
      oPInt64,    // BigInt  use .AsInt64()
      oPTime,     // Time    use  PTime( "Value" ) 
      oPGUID      // GUID    use  PGUID( "Value" ) To Be Implemented...?
    };

    /** Datasources that are supported by this implementation
    used in the PODBC::DataSource Function.
    */

    enum DataSources
    {
      mySQL,      
      MSSQL,      
      Oracle,      
      IBM_DB2,
      DBASE,
      Paradox,
      Excel,
      Ascii,
      Foxpro,
      MSAccess,
      postgreSQL
    };

    /** MSSQL protocols.If your interested?
    */
    enum MSSQLProtocols
    {
      MSSQLNamedPipes,
      MSSQLWinSock,
      MSSQLIPX,
      MSSQLBanyan,
      MSSQLRPC
    };

    //@}

    /**@name Connection Class */
    //@{
    /** This class is a multipurpose use
    class for storing parameters when
    initiating connection to DataSource.
    Not all field are required. By default
    all non-essential params are set to a 
    datasource specific default value.
    */
    class ConnectData
    {
    public:
      PFilePath DBPath;    /// Database file Path (not Oracle,xxSQL)
      PString DefDir;     /// Used with Paradox/DBase/Excel (& mySQL db)
      PString User;       /// UserName
      PString Pass;       /// Password
      PBoolean Excl_Trust;     /// Whether Datasource is locked or Trusted.
      PString Host;       /// URL for Host Datasouce xxSQL
      int Port;         /// Port to connect to mySQL
      int opt;         /// General Option Value.mySQL & Paradox
    };
    //@}


    /**@name Database Field Class */
    //@{
    /** Class for Field Data
    */
    class Row;
    class Field : public PObject
    {
        PCLASSINFO(Field, PObject);
      public:

        /** SQL compliant Bound DataTypes.
        The appropriate Field is bound
        to the SQL Driver and alters 
        when a new record is fetched.
        */
        class Bind
        {
          public:
            PString          sbin;      /// Strings & Binary Data
            PString          sbinlong;  /// Long Data
            short int        ssint;     /// Short Integer    SQLSMALLINT
            long int         slint;     /// Integer        SQLINTEGER
            double           sdoub;     /// Double        SQLDOUBLE
            unsigned char    sbit;      /// Bit          SQLCHAR
            unsigned char *  suchar;    /// Unsigned char    SQLCHAR *
            PInt64           sbint;     /// Bit Integer      SQLBIGINT
            DATE_STRUCT      date;      /// Date Structure  
            TIME_STRUCT      time;      /// Time Structure
            TIMESTAMP_STRUCT timestamp; /// TimeStamp Structure
            SQLGUID          guid;      /// GUID Structure (not Fully Supported)
            SQLLEN           dataLen;   /// DataLength pointer (StrLen_or_Ind for Col Bind)
        };

        /** Post the Changes back to the Database
        */
        PBoolean Post();

        /** Returns a String representation of the field.
        */
        PString operator=(const PString & str);

        /** Display the Field Data as String
        */
        PString AsString();  

        /** Set the Field Data. Note a Post() must be called
        to post the changes back to the database.
        */
        void SetValue(PString value);  /// Set the Value

        /** Initialise/Set the Default values for Field of New Record
        */
        void SetDefaultValues();

        /** DataFragment Data is broken into fragment to be passed
        to the Database
        */
        PBoolean DataFragment(PString & Buffer ,PINDEX & fragment, SQLINTEGER & size);

        /** Settings
        */
        /// Data
        Bind  Data;       /// Data Field to ODBC Bind to
        PwType  Type;       /// pwlib Type for conversion
        FieldTypes ODBCType;   /// ODBC Type (For saving/Conversion)

        /// Column
        PString Name;       /// Column Name
        PINDEX col;       /// Column Number (For Saving/Conversion)

        /// Column Attributes
        PBoolean isReadOnly;     /// Is Field Readonly
        PBoolean isNullable;     /// Allows Nulls
        PBoolean isAutoInc;     /// Field AutoIncrements
        int Decimals;       /// Number of decimal places to Round
        PBoolean LongData;     /// LongData Length is Required

        /// RecordHolder Reference
        Row * row;       /// Back Reference to the Row
    };
    //@}


    /**@name Database Row Class */
    //@{ 
    /** This class functions as a simple wrapper 
    of the PODBCStmt class to fetch/Save
    data to the Datasource. Data is fetched
    on a need to basis and not cached except
    to create a new row.
    */
    class Row : public PObject
    {
      public:

        /** Constructor
        Create a Dummy row of data to act as a 
        Record Marker. Template Field are created
        and Stored in a PARRAY.
        */
        Row(PODBCStmt * stmt);

        /** Retrieve Field Data given the specifed column.
        Note: Columns atart at 1 and not exceed PODBCStmt::GetColumnCount()
        */
        Field & Column(PINDEX col);

        /** Retreive Field Data given the Column Name
        */
        Field & Column(PString name);

        /** Retrieve the Column Names
        */
        PStringArray ColumnNames();

        /** Columns. The Number of Columns in the RecordSet
        */
        PINDEX Columns();

        /** Rows  The Number of Rows 
        */
        PINDEX Rows();

        /** Retrieve Field Data given specified column
        */
        Field & operator[] (PINDEX col);

        /** Retrieve Field Data given the column Name.
        */
        Field & operator[] (PString col);

        /** Navigate to Specified Row
        */
        PBoolean Navigate(PINDEX row);

        /** SetNewRow Set New Row for input
        */
        void SetNewRow();

        /** Post the Row back to the Database.
        When Row::NewRow is true the data
        can be posted back to the Database;
        If Edit Invoked then releasea the
        RowHandler for Navigation.
        */
        PBoolean Post();

        /** Delete the Current Record from the
        RecordSet
        */
        PBoolean Delete(PINDEX row =0);

        PODBCRecord * rec;      /// Record Structure

        PINDEX CurRow;          /// Current Row
        PBoolean NewRow;        /// Flag to Indicate New Row (requires either Post or Delete)
        PINDEX RowCount;      /// Number of Rows.

      protected:
        PArray<Field> Fields;    /// PODBC::Field Array Cache (Used for New Row)
    };
    //@}

    /** PODBC::Table
    This is the main Class to access Data returned by a Select Query.
    The Table does not actually create the RecordSet but acts as a wrapper 
    to the driver to access the cached data in the Driver.
    */
    class Table : public PObject
    {
      public:

        /**@name Constructor/Deconstructor */
        //@{ 
        /** Constructor
        Using the HDBC and TableName/Select SQL Query 
        creates a virtual Table in the OBDC driver.
        */
        Table(PODBC * odbc, PString Query);

        /** Deconstructor
        */
        ~Table();
        //@}

        /**@name Data Storage */
        //@{
        /** Add New Row
        */
        Row NewRow();

        /** Delete Row 0 indicates Current Row
        */
        PBoolean DeleteRow(PINDEX row = 0);

        /** Post Update back to Database
        */
        PBoolean Post();
        //@}

        /**@name Utilities */
        //@{
        /** Rows. Returns the Number of Rows in the Resultant RecordSet
        */
        PINDEX Rows();

        /** Columns. Returns the Number of Columns in the Resultant RecordSet
        */
        PINDEX Columns();

        /** ColumnNames. Return the list of column Names of the Resultant RecordSet
        */
        PStringArray ColumnNames();

        /** Obtain the Record Handler. This can be used as a Template to obtain
        Record Information. A call to tablename[i] will update the recordHandler
        with the Values contained in i Record. 
        */
        Row & RecordHandler();

        /** Row return the fetched row in the Cached RecordSet. An Array of PODBC::Field
        */
        Row & operator[] (PINDEX row);

        /** Returns the Field data at a predetermined position in the Resultant
        RecordSet. It Fetches the Row than isolates the Column from the fetched 
        data.
        */
        Field & operator() (PINDEX row, PINDEX col);

        /** Returns the indicated Column Holder for the RecordSet,
        This can be used for iterative Row calls.
        */
        Field & Column(PINDEX col);

        /** Returns the indicated Column Holder Name for the RecordSet,  
        */
        Field & Column(PString Name);
        //@}

      protected:
        PODBCStmt stmt;      /// ODBC Fetched Statement Info
        PString tableName;    /// Name of the Fetched Table (if used in Constructor)
        Row * RowHandler;      /// row Handler
    };

    /**@name Data Queries */
    //@{ 
    /** Load a specified Table/Stored Query or 
    General 'SELECT' SQL Query.
    This function will return a PODBC::Table for
    further analysis. Do Not Use this Function for
    any other SQL statements other than SELECT.
    */
    Table LoadTable(PString table);

    /** Added Information to the DataSource. Use this 
    function if you just want to use a SQL statement
    to add data to a datasource without retreiving the
    data itself. ie "UPDATE" "APPEND" "INSERT" queries.
    */
    PBoolean Query(PString Query);
    //@}


    /**@name DataSource Access */
    //@{ 
    /** DataSource
    This is the main function to call to contact a
    DataSource. Source specifies the Type of DataSource
    to contact and the Data parameter contain the relevent
    connection information. You can choose to call this function
    or use the specific Connection function.
    */
    PBoolean DataSource(DataSources Source, ConnectData Data);

    /** General Connect Function
    Custom connection strings should call this 
    to connect Don't ask why its LPCTSTR!
    */
    virtual PBoolean Connect(LPCTSTR svSource);

    /** Connect to IBM DB2 DataSource
    */
    PBoolean Connect_DB2(PFilePath DBPath);

    /** Connect to MS Office excel spreadsheet
    */
    PBoolean Connect_XLS(PFilePath XLSPath,PString DefDir = "");

    /** Connect to an ascii text or cvs file
    */
    PBoolean Connect_TXT(PFilePath TXTPath);

    /** Connect to a Foxpro dataSource
    */
    PBoolean Connect_FOX(PFilePath DBPath,PString User = "",
      PString Pass = "",PString Type= "DBF",
      PBoolean Exclusive=false);

    /** Connect to a MS Access *.mdb DataSource.
    */
    PBoolean Connect_MDB(PFilePath MDBPath,PString User ="",
      PString Pass = "",PBoolean Exclusive=false);

    /** Connect to a paradox database datastore
    */
    PBoolean Connect_PDOX(PDirectory DBPath,PDirectory DefaultDir,
      int version =5);

    /** Connect to an Oracle Datasource
    */
    PBoolean Connect_Oracle(PString Server,PString User="", PString Pass="");

    /** Connect to a DBase DataStore
    */
    PBoolean Connect_DBASE(PDirectory DBPath);

    /** Connect to a MS SQL Server
    */
    PBoolean Connect_MSSQL(PString User="",PString Pass="", 
      PString Host ="(local)",PBoolean Trusted = true, 
      MSSQLProtocols Proto=MSSQLNamedPipes);

    /** Connect to a mySQL Server
    */
    PBoolean Connect_mySQL(PString User="",PString Pass="",
      PString Host= "localhost",
      int Port=3306,int Option=0);

    /** Connect to a mySQL Server's specified DataBase.
    */
    PBoolean ConnectDB_mySQL(PString DB,PString User="",
      PString Pass="",PString Host= "localhost",
      int Port=3306,int Option=0);

    /** Connect to a postgreSQL Server
    */
    PBoolean Connect_postgreSQL(PString DB,PString User,
      PString Pass,PString Host, int Port=5432,int Option=0);

    /** General Disconnect from DataSource.
    */
    void Disconnect();
    //@}

    /**@name Utilities */
    //@{ 
    /** Retrieve a List of Tables in the Datasource
    use the option field to specify the type of
    data to access. ie "TABLE" or "VIEW" (further dev req'd)
    */
    PStringArray TableList(PString option = "");

    /** Check whether their is a limit to Datalength
    when obtaining Long Data
    */
    PBoolean NeedLongDataLen();

    /** OnSQL Error
    */
    virtual void OnSQLError(PString RetCode, PString RetString) {};


    /** Set the Number of Decimal places to
    round to By Default it is 4. However if the field
    decimal places is less then Precision Value the 
    field rounding will be used. This must be set prior
    to calling LoadTable()
    */
    void SetPrecision(int Digit);

    /** Set the Time Display Format
    */
    void SetTimeFormat(PTime::TimeFormat tformat);

    /** Operator Handle DataBase Connection
    */
    operator HDBC() { return m_hDBC; };
    //@}

    PODBC::DataSources  dbase; /// Database Type connected to

  protected:
    SQLRETURN       m_nReturn;      // Internal SQL Error code
    HENV            m_hEnv;         // Handle to environment
    HDBC            m_hDBC;         // Handle to database connection
};


/**    
  DSN (Data Source Name) Connection. The connection settings 
  have been preconfiured in the MDAC (Microsoft Data Access Component)
  and is called using those Preset Settings. Calling the PDSNConnection::Connect
  has the same effect and is a replaceable for PODBC::DataSource,
 */
class PDSNConnection : public PODBC
{
    PCLASSINFO(PDSNConnection, PODBC);

  public:
    /**@name Constructor/Deconstructor */
    //@{
    PDSNConnection();
    ~PDSNConnection();
    //@}

    /**@name Connection/Disconnect */
    //@{
    /** Connect to the MDAC using a pre-existing MDAC Defined DataSource
    This is different than calling PODBC::DataSource in that the 
    Data Source is known defined externally within MDAC,
    */
    PBoolean Connect( PString Source ,PString Username, PString Password);
};


 //--
/** PODBCRecord
    This Class is used to analyse the fetched data and handles
    Data Conversion/Read Write operations. It is used in conjuction
    with the PODBCStmt Class
*/

class PODBCRecord : public PObject
{
    PCLASSINFO(PODBCRecord, PObject);

  public:
    /**@name Constructor/Deconstructor */
    //@{ 
    /** Constructor 
    */
    PODBCRecord(PODBCStmt * hStmt);

    /** Deconstructor
    */
    ~PODBCRecord(){};
    //@}

    /**@name Data Collection/Saving */
    //@{ 
    /** Data: Main Call to retrieve and convert Field Data 
    and return the information in the PODBC::Field structure.
    */
    void Data(PINDEX Column, PODBC::Field & field);

    /** InternalGetData is call when retrieving string or large binary 
    data where the size is indetermined. The Function can be iteratively
    called until the function returns false.
    */
    PBoolean InternalGetData(
      USHORT Column,
      LPVOID pBuffer, 
      ULONG pBufLen,
      SQLINTEGER * dataLen=NULL,
      int Type=SQL_C_DEFAULT
      );

    /* Get Long Character Data. Long Data fields cannot be bound
    and Data must be Got from the RecordSet.
    */
    PString GetLongData(PINDEX Column);

    /** Post the new record back to the RecordSet;
    */
    PBoolean PostNew(PODBC::Row & rec);

    /** Post the Updated record back to the RecordSet;
    */
    PBoolean PostUpdate(PODBC::Row & rec);

    /** Post a Delete command to the RecordSet; Default
    1 Row is deleted.
    */
    PBoolean PostDelete(PINDEX row= 1);

    /** Check for and Save Long Data
    */
    PBoolean InternalSaveLongData(SQLRETURN nRet,PODBC::Row & rec);

    /** InternalBindColumn for Data input.
    */
    PBoolean InternalBindColumn(
      USHORT Column,LPVOID pBuffer,
      ULONG pBufferSize,
      LONG * pReturnedBufferSize=NULL,
      USHORT nType=SQL_C_TCHAR
      );
    //@}

    /**@name Data Information */
    //@{ 
    /** ColumnByName returns the column number of the column name
    If not found returns column value of 0;
    */
    PINDEX ColumnByName(PString Column);

    /** ColumnCount No of columns
    */
    PINDEX ColumnCount();

    /** ColumnTypes
    */
    PODBC::FieldTypes ColumnType(PINDEX Column );

    /** Column Size
    */
    DWORD ColumnSize( PINDEX Column );

    /** Column Scale
    */
    DWORD ColumnScale( PINDEX Column );

    /** Column Name
    */
    PString ColumnName( PINDEX Column);

    /** ColumnPrecision Get the Number of Decimal places
    if Precision is set the precision is set to the
    lessor of the Two.
    */
    unsigned int ColumnPrecision( PINDEX Column );

    /** IsColumn Nullable. Accepts NULL value
    */
    PBoolean IsColumnNullable( PINDEX Column );

    /** IsColumn Updateable ie is not ReadOnly
    */
    PBoolean IsColumnUpdatable( PINDEX Column );

    /** IsColumnAutoIndex (ie don't give default Value)
    */
    PBoolean IsColumnAutoIndex( PINDEX Column );

    //@}

    /**@name Data Conversion Settings */
    //@{ 
    /** Conversion Settings
    */
    static unsigned int Precision;      /// Double Real Float Decimal digit rounding def= 4;
    static int MaxCharSize;          /// Long Data Limit KBytes def = 56; (56 Kbytes)
    static PTime::TimeFormat TimeFormat;/// Time Format
    //@}

  protected:
    HSTMT m_hStmt;
    PODBCStmt * Stmt;          /// Statement Class
    PODBC::DataSources dbase;      /// Database Type connecting to

  friend class PODBC::Field;
  friend class PODBC::Row;
};

#endif // P_ODBC

#endif // PTLIB_PODBC_H


// End Of File ///////////////////////////////////////////////////////////////