00001
00002
00003
00004
00005
00006
00007
00008 #include "jpeg.h"
00009 #include <assert.h>
00010 #include <string.h>
00011 #include <stdlib.h>
00012 #include <stdio.h>
00013 #ifndef _WIN32
00014 #include <dlfcn.h>
00015 #endif
00016
00017 #include <iostream>
00018
00019 using namespace std;
00020
00021 #ifdef __APPLE__
00022 #define BYTE unsigned char
00023 #define LONG long
00024 #define PRIVATE private
00025 #define PUBLIC
00026 #endif // __APPLE__
00027
00028 const unsigned int MAX_ALLOWED = 64 * 1024;
00029 const int put_buff_size = DEFAULT_PUT_QUEUE_SIZE;
00030 static BYTE myBuf[2][put_buff_size];
00031
00032
00033
00034
00035
00036 #ifndef _WIN32 // Linux/Solaris specific handling
00037
00038 PRIVATE LONG defer_function(PIC_PARM *p, RESPONSE res);
00039
00040 bool pegasusInitialized = false;
00041 void* Peg_handle;
00042 PUBLIC RESPONSE DLLEXPORTWINAPI (*Peg) (PIC_PARM PICHUGE *p, REQUEST req);
00043 PUBLIC BOOL DLLEXPORTWINAPI (*PegQuery) (PIC_PARM PICHUGE *p);
00044 PUBLIC LONG DLLEXPORTWINAPI (*PegLoad) (
00045 OPERATION Op,
00046 LONG ParmVer,
00047 char PICFAR *Path);
00048
00049 PUBLIC LONG DLLEXPORTWINAPI (*PegLoadFromRes) (
00050 OPERATION Op,
00051 LONG ParmVer,
00052 char PICFAR *Path,
00053 DWORD hInstance);
00054 PUBLIC BOOL DLLEXPORTWINAPI (*PegLibInit) (DWORD hInstance);
00055
00056 PUBLIC void DLLEXPORTWINAPI (*PegLibTerm) (void);
00057
00058 PUBLIC void DLLEXPORTWINAPI (*PegLibThreadInit) (void);
00059
00060 PUBLIC void DLLEXPORTWINAPI (*PegLibThreadTerm) (void);
00061
00062 void InitPegasus()
00063 {
00064 #ifdef linux
00065 Peg_handle = dlopen("./libs/libpicl20.so", RTLD_LAZY);
00066 #else
00067 Peg_handle = dlopen("./libs/libpicu20.so", RTLD_LAZY);
00068 #endif
00069 if (Peg_handle == NULL) {
00070 fputs(dlerror(),stderr);
00071 exit(0);
00072 }
00073 Peg = (RESPONSE DLLEXPORTWINAPI (*) (PIC_PARM PICHUGE *p, REQUEST req))dlsym(Peg_handle,"Pegasus");
00074 PegQuery = (PUBLIC BOOL DLLEXPORTWINAPI (*) (PIC_PARM PICHUGE *p))dlsym(Peg_handle,"PegasusQuery");
00075 PegLoad = (PUBLIC LONG DLLEXPORTWINAPI (*) (
00076 OPERATION Op,
00077 LONG ParmVer,
00078 char PICFAR *Path))dlsym(Peg_handle,"PegasusLoad");
00079
00080 PegLoadFromRes = (PUBLIC LONG DLLEXPORTWINAPI (*) (
00081 OPERATION Op,
00082 LONG ParmVer,
00083 char PICFAR *Path,
00084 DWORD hInstance))dlsym(Peg_handle,"PegasuLoadFromres");
00085
00086 PegLibInit = (PUBLIC BOOL DLLEXPORTWINAPI (*) (DWORD hInstance))dlsym(Peg_handle,"PegasusLibInit");
00087 PegLibThreadInit = (PUBLIC void DLLEXPORTWINAPI (*) (void))dlsym(Peg_handle,"PegasusLibThreadInit");
00088 PegLibThreadTerm = (PUBLIC void DLLEXPORTWINAPI (*) (void))dlsym(Peg_handle,"PegasusLibThreadTerm");
00089
00090 if ((PegQuery != NULL) && (Peg != NULL) && (PegLoad != NULL) && (PegLibInit != NULL) &&
00091 (PegLibThreadInit != NULL))
00092 cerr << "so far so good\n";
00093 else
00094 exit(0);
00095
00096 LONG res = (*PegLoad)(OP_D2S,CURRENT_PARMVER,"./libs/");
00097 res = (*PegLoad)(OP_S2D,CURRENT_PARMVER,"./libs/");
00098
00099 }
00100
00101 #define Pegasus (*Peg)
00102 #define PegasusQuery (*PegQuery)
00103 #define PegasusLibInit (*PegLibInit)
00104 #define PegasusLibThreadInit (*PegLibThreadInit)
00105 #define PegasusLibThreadTerm (*PegLibThreadTerm)
00106
00107
00108
00109
00110
00111 PRIVATE LONG defer_function(PIC_PARM *p, RESPONSE res)
00112 {
00113 cerr << "\n\n Ooops \t" << res << "\n";
00114 return(0);
00115 }
00116
00117
00118 void MessageBox(void* dummy1, char* msg, void* dummy2, int ok)
00119 { cerr << msg << endl; }
00120 #define MB_OK 0
00121
00122 #else // now for compatibility with Windows.
00123
00124 extern HINSTANCE hInst;
00125 bool pegasusInitialized = false;
00126 void InitPegasus() {return;}
00127
00128 #endif
00129
00130
00131
00132
00133
00134 LONG ExpandJPEGTo24BitDIB(
00135 LPBYTE pbInputBuffer,
00136 DWORD dwInputLength,
00137 LPBYTE *ppbOutputBuffer,
00138 DWORD *pdwOutputLength)
00139 {
00140 if (!pegasusInitialized)
00141 {
00142 InitPegasus();
00143 pegasusInitialized = true;
00144 }
00145
00146 PIC_PARM PicParm;
00147 RESPONSE Response;
00148
00149
00150 memset(&PicParm, 0, sizeof(PicParm));
00151 PicParm.ParmSize = sizeof(PicParm);
00152 PicParm.ParmVer = CURRENT_PARMVER;
00153 PicParm.ParmVerMinor = 1;
00154 #ifndef _WIN32
00155 PicParm.DeferFn = &defer_function;
00156 #endif
00157
00158 PicParm.Get.Start = pbInputBuffer;
00159 PicParm.Get.End = pbInputBuffer + dwInputLength;
00160
00161
00162 PicParm.Get.Front = PicParm.Get.Start;
00163 PicParm.Get.Rear = PicParm.Get.End;
00164 PicParm.Get.QFlags = Q_EOF;
00165 #ifndef _WIN32
00166 PicParm.Flags |= F_UseDeferFn;
00167 #endif
00168
00169
00170
00171 PicParm.u.QRY.BitFlagsReq = QBIT_BICOMPRESSION;
00172 if ( !PegasusQuery(&PicParm) ||
00173 ( PicParm.Head.biCompression != BI_JPEG &&
00174 PicParm.Head.biCompression != BI_PICJ ) )
00175 return ( ERR_BAD_IMAGE_TYPE );
00176
00177
00178 PicParm.Op = OP_S2D;
00179
00180 memset(&PicParm.u.S2D, 0, sizeof(PicParm.u.S2D));
00181 PicParm.u.S2D.DibSize = 24;
00182
00183
00184 Response = Pegasus(&PicParm, REQ_INIT);
00185
00186 if ( Response == RES_ERR )
00187 return ( PicParm.Status );
00188 assert(Response == RES_DONE);
00189
00190
00191 *pdwOutputLength = PicParm.Head.biHeight * PicParm.u.S2D.WidthPad;
00192
00193 *ppbOutputBuffer = (unsigned char*)malloc(*pdwOutputLength);
00194 if ( *ppbOutputBuffer == 0 )
00195 {
00196 Pegasus(&PicParm, REQ_TERM);
00197 return ( ERR_OUT_OF_SPACE );
00198 }
00199
00200 PicParm.Put.Start = *ppbOutputBuffer;
00201 PicParm.Put.End = *ppbOutputBuffer + *pdwOutputLength;
00202
00203
00204 PicParm.Put.Front = PicParm.Put.End;
00205 PicParm.Put.Rear = PicParm.Put.Front;
00206
00207
00208
00209 Response = Pegasus(&PicParm, REQ_EXEC);
00210
00211 if ( Response == RES_ERR )
00212 {
00213
00214 free(*ppbOutputBuffer);
00215 return ( PicParm.Status );
00216 }
00217 assert(Response == RES_DONE);
00218
00219
00220 Response = Pegasus(&PicParm, REQ_TERM);
00221 assert(Response == RES_DONE);
00222
00223 return ( ERR_NONE );
00224 }
00225
00226
00227
00228
00229
00230 LONG CompressToJPEG(
00231 LPBYTE pbInputBuffer,
00232 DWORD dwInputLength,
00233 LPBYTE* ppbOutputBuffer,
00234 DWORD* pdwOutputLength,
00235 int code
00236 )
00237 {
00238
00239 #ifdef _WIN32
00240
00241
00242 #endif
00243
00244 if (!pegasusInitialized)
00245 {
00246 InitPegasus();
00247 pegasusInitialized = true;
00248 }
00249
00250 PIC_PARM PicParm;
00251 RESPONSE Response;
00252
00253
00254 memset(&PicParm, 0, sizeof(PicParm));
00255 PicParm.ParmSize = sizeof(PicParm);
00256 PicParm.ParmVer = CURRENT_PARMVER;
00257 PicParm.ParmVerMinor = 1;
00258 #ifndef _WIN32
00259 PicParm.DeferFn = &defer_function;
00260 #endif
00261
00262
00263 PicParm.Get.Start = pbInputBuffer;
00264 PicParm.Get.End = pbInputBuffer + dwInputLength;
00265
00266
00267 PicParm.Get.Front = PicParm.Get.Start;
00268 PicParm.Get.Rear = PicParm.Get.End;
00269
00270 #ifndef _WIN32
00271 PicParm.Flags |= F_UseDeferFn;
00272 #endif
00273
00274
00275
00276 PicParm.u.QRY.BitFlagsReq = QBIT_BICOMPRESSION;
00277 if ( !PegasusQuery(&PicParm)
00278 ||
00279 ( PicParm.Head.biCompression != BI_RGB ))
00280 return ( ERR_BAD_IMAGE_TYPE );
00281 memset(&PicParm.u.QRY, 0, sizeof(PicParm.u.QRY));
00282 PicParm.Get.QFlags |= Q_EOF;
00283
00284
00285 PicParm.Op = OP_D2S;
00286
00287 memset(&PicParm.u.D2S, 0, sizeof(PicParm.u.D2S));
00288
00289
00290 PicParm.Get.Front += 54;
00291 PicParm.u.D2S.LumFactor = 24;
00292 PicParm.u.D2S.ChromFactor = 30;
00293 PicParm.u.D2S.SubSampling = 2;
00294 PicParm.u.D2S.JpegType = JT_RAW;
00295 PicParm.u.D2S.PicFlags |= PF_OptimizeHuff;
00296
00297
00298 PicParm.Head.biHeight = -PicParm.Head.biHeight;
00299
00300
00301 PicParm.Put.Start = myBuf[code];
00302 PicParm.Put.Front = PicParm.Put.Rear = PicParm.Put.Start + 3;
00303 PicParm.Put.End = PicParm.Put.Start + put_buff_size;
00304
00305
00306
00307 Response = Pegasus(&PicParm, REQ_INIT);
00308 if ( Response == RES_ERR )
00309 return ( PicParm.Status );
00310 assert(Response == RES_DONE);
00311
00312 if(PicParm.Get.QFlags & Q_REVERSE)
00313 {
00314 PicParm.Get.Rear = PicParm.Get.Front;
00315 PicParm.Get.Front += PicParm.Head.biSizeImage;
00316 }
00317
00318
00319 Response = Pegasus(&PicParm, REQ_EXEC);
00320
00321 if ( Response == RES_ERR )
00322 {
00323 return ( PicParm.Status );
00324 }
00325 assert(Response == RES_DONE);
00326
00327
00328 *pdwOutputLength = PicParm.Put.Rear - PicParm.Put.Front;
00329
00330 memcpy(*ppbOutputBuffer,PicParm.Put.Front,*pdwOutputLength);
00331
00332 Response = Pegasus(&PicParm, REQ_TERM);
00333 assert(Response == RES_DONE);
00334
00335
00336 #ifdef _WIN32
00337
00338
00339 #endif
00340
00341
00342 return ( ERR_NONE );
00343 }
00344