メインページ | アルファベット順一覧 | 構成 | ファイル一覧 | 構成メンバ | ファイルメンバ | 関連ページ

# dkcSingleList.c

説明を見る。

    00001
    00007 #define DKUTIL_C_SINGLE_LIST_C
    00008 #include "dkcSingleList.h"
    00009 #include "dkcStdio.h"
    00010
    00011
    00012 //DKC_SINGLELISTを初期化
    00013 static int WINAPI dkcNewSingleList(DKC_SINGLELIST *ptr,const void *data,size_t size)
    00014 {
    00015     void *p = NULL;
    00016     if(NULL==ptr) return edk_ArgumentException;
    00017     if(ptr->mBuff) return edk_ArgumentException;
    00018     if(ptr->mNext) return edk_FAILED;
    00019
    00020     p = dkcAllocate(size);
    00021     if(NULL==p) return edk_OutOfMemory;
    00022
    00023     if(NULL != data && 0 != size){
    00024         if(DKUTIL_FAILED(dkc_memcpy(p,size,data,size))){
    00025             return edk_FAILED;
    00026         }
    00027     }
    00028
    00029     ptr->mBuff = (BYTE *)p;
    00030     ptr->mSize = size;
    00031     ptr->mNext = NULL;
    00032
    00033     return edk_SUCCEEDED;
    00034 }
    00035
    00043 static int WINAPI dkcDeleteSingleList(DKC_SINGLELIST *ptr){
    00044     DKC_SINGLELIST *p = NULL;
    00045     if(NULL==ptr) return edk_ArgumentException;
    00046     if(NULL==ptr->mBuff) return edk_ArgumentException;
    00047
    00048     for(p = ptr;;){
    00049         p = dkcSingleListErase(p);
    00050         if(p==NULL) break;
    00051     }
    00052     return edk_SUCCEEDED;
    00053 }
    00054
    00055 //シングルリスト領域を得る。
    00056 DKC_SINGLELIST * WINAPI dkcAllocSingleList(const void *data,size_t size){
    00057     DKC_SINGLELIST *p = NULL;
    00058     p = (DKC_SINGLELIST *)dkcAllocate(sizeof(DKC_SINGLELIST));
    00059     //p dkcAllocate(size);
    00060     if(DKUTIL_FAILED(dkcNewSingleList(p,data,size))){
    00061         goto Error;
    00062     }
    00063     return p;
    00064 Error:
    00065     dkcFree((void **)&p);
    00066     return NULL;
    00067 }
    00068
    00069 //dkcAllocNewSingleList()で確保したリスト領域と
    00070 int WINAPI dkcFreeSingleList(DKC_SINGLELIST **ptr){
    00071     if(NULL==ptr) return edk_FAILED;
    00072     if(DKUTIL_FAILED(dkcDeleteSingleList(*ptr))){
    00073         return edk_FAILED;
    00074     }
    00075     //dkcFree((void **)*ptr);
    00076     return edk_SUCCEEDED;
    00077 }
    00078
    00079 void WINAPI dkcSingleListChain(DKC_SINGLELIST *ptr,DKC_SINGLELIST *nextp)
    00080 {
    00081     DKC_SINGLELIST *t=NULL;
    00082
    00083     //バカヤロー条件
    00084     dkcmNOT_ASSERT(NULL==ptr || NULL==nextp);
    00085
    00086     if(ptr->mNext)
    00087     {//次へのポインタがあった場合
    00088         t = ptr->mNext;//保存。
    00089         ptr->mNext = nextp;//ぶち込む。
    00090         nextp->mNext = t;//保存していたのをぶち込む
    00091
    00092     }else
    00093     {//次へのポインタがなかった場合。
    00094         ptr->mNext = nextp;//すぐぶち込む。
    00095     }
    00096
    00097
    00098 }
    00099 int WINAPI dkcSingleListInsert(DKC_SINGLELIST *ptr,const void *data,size_t size){
    00100     DKC_SINGLELIST *p;
    00101     if(NULL==ptr) return edk_ArgumentException;
    00102
    00103     p = dkcAllocSingleList(data,size);
    00104     if(NULL==p) return edk_FAILED;
    00105     dkcmNOT_ASSERT(p->mNext);//念のため。
    00106
    00107     dkcSingleListChain(ptr,p);
    00108
    00109     return edk_SUCCEEDED;
    00110 }
    00111
    00112 DKC_SINGLELIST * WINAPI dkcSingleListErase(DKC_SINGLELIST *ptr){
    00113     DKC_SINGLELIST *t = NULL;
    00114     if(NULL==ptr) return NULL;
    00115     //if(NULL==ptr->mBuff) return NULL;//メモリリークの原因になるかも？
    00116
    00117     dkcFree((void **)&ptr->mBuff);
    00118     t = ptr->mNext;
    00119     dkcFree((void **)&ptr);
    00120     return t;
    00121 }
    00122
    00123 int WINAPI dkcGetSingleListBuffer(DKC_SINGLELIST *ptr,void *data,size_t size){
    00124     if(NULL==ptr) return edk_ArgumentException;
    00125     if(NULL==ptr->mBuff) return edk_FAILED;
    00126     //if(ptr->mSize < size) return edk_BufferOverFlow;
    00127     return dkc_memcpy(data,size,ptr->mBuff,ptr->mSize);
    00128 }
    00129
    00130 DKC_BUFFER* WINAPI dkcAllocSingleListBuffer(const DKC_SINGLELIST *ptr)
    00131 {
    00132     DKC_BUFFER *p;
    00133     if(NULL==ptr) return NULL;
    00134     p = dkcAllocBuffer(ptr->mBuff,ptr->mSize);
    00135     return p;
    00136 }
    00137
    00138
    00139 /*
    00140 DKC_SINGLELIST * WINAPI dkcAllocSingleListDeserialize(DKC_DESERIALIZE *se)
    00141 {
    00142     DKC_SINGLELIST *p,*tp,*beginp;
    00143     DKC_SINGLELIST t;
    00144     size_t read,c,i;
    00145     UINT sig;
    00146
    00147     dkcmNOT_ASSERT(NULL==se);
    00148     DKUTIL_MEMZERO(&t,sizeof(t));
    00149     //シグネチャを取得
    00150     dkcDeserializeRead(se,&sig,sizeof(sig),&read);
    00151     //そんな馬鹿な！判定
    00152     if(read != sizeof(sig) || edkcSerializeIDSingleList != sig)
    00153     {
    00154         return NULL;
    00155     }
    00156     //数を取得
    00157     dkcDeserializeRead(se,&c,sizeof(c),&read);
    00158
    00159     //構造体を取得。
    00160     dkcDeserializeRead(se,&t,sizeof(DKC_SINGLELIST),&read);
    00161     p = dkcAllocSingleList(NULL,t.mSize);
    00162     //バッファ領域を取得。
    00163     dkcDeserializeRead(se,p->mBuff,p->mSize,&read);
    00164
    00165     beginp = p;
    00166     for(i=0;i<c;i++)
    00167     {
    00168         //構造体を取得。
    00169         dkcDeserializeRead(se,&t,sizeof(DKC_SINGLELIST),&read);
    00170         //保存。
    00171         tp = p;
    00172         //リスト生成
    00173         p = dkcAllocSingleList(NULL,t.mSize);
    00174         //バッファ領域を取得。
    00175         dkcDeserializeRead(se,p->mBuff,p->mSize,&read);
    00176         //チェイン
    00177         dkcSingleListChain(tp,p);
    00178
    00179     }
    00180     return beginp;
    00181 }
    00182
    00183 void WINAPI dkcSingleListSerialize(const DKC_SINGLELIST *ptr,DKC_SERIALIZE *se)
    00184 {
    00185     DKC_SINGLELIST *tp = (DKC_SINGLELIST *)ptr;
    00186     size_t c; //counter
    00187     UINT sig;//signature
    00188     //size_t i; //for counter
    00189     dkcmNOT_ASSERT(NULL==ptr);
    00190
    00191     sig = edkcSerializeIDSingleList;
    00192     //シグネチャを保存
    00193     dkcSerializeWrite(se,&sig,sizeof(sig));
    00194
    00195     for(c=0;;c++)//c=0はSerialize,Deserialize統一しないと行けない。
    00196     {//liner count... very slow...
    00197         if(NULL == tp->mNext) break;
    00198         tp = tp->mNext;
    00199     }
    00200     //数を入れる。
    00201     dkcSerializeWrite(se,&c,sizeof(c));
    00202
    00203     tp = (DKC_SINGLELIST *)ptr;
    00204     for(;;){
    00205         //構造体を入れる。
    00206         dkcSerializeWrite(se,tp,sizeof(DKC_SINGLELIST));
    00207         //バッファ領域を入れる。
    00208         dkcSerializeWrite(se,tp->mBuff,tp->mSize);
    00209         if(NULL == tp->mNext){
    00210             break;
    00211         }
    00212         tp = tp->mNext;//次へのポインタ
    00213     }
    00214
    00215 }
    00216 */
    00217
    00218 int WINAPI dkcSingleListGetBuffer(DKC_SINGLELIST *ptr,void *data,size_t size)
    00219 {
    00220     if(NULL==ptr || NULL==data || 0==size){
    00221         return edk_FAILED;
    00222     }
    00223     return dkc_memcpy(data,size,ptr->mBuff,ptr->mSize);
    00224 }
    00225
    00226 int WINAPI dkcSingleListSetBuffer(DKC_SINGLELIST *ptr,const void *data,size_t size)
    00227 {
    00228     void *NewPtr;
    00229
    00230     if(NULL==ptr || NULL==data || 0==size){
    00231         return edk_FAILED;
    00232     }
    00233
    00234     if(ptr->mSize < size){
    00235         if(DKUTIL_FAILED(dkcReallocate(&NewPtr,size,(void **)&(ptr->mBuff)))){
    00236             return edk_FAILED;
    00237         }
    00238
    00239         ptr->mBuff =(BYTE *) NewPtr;
    00240         ptr->mSize = size;
    00241     }
    00242
    00243     if(DKUTIL_FAILED(dkc_memcpy(ptr->mBuff,ptr->mSize,data,size))){
    00244         return edk_FAILED;
    00245     }
    00246
    00247     return edk_SUCCEEDED;
    00248 }
    00249 size_t WINAPI dkcSingleListSize(DKC_SINGLELIST *top)
    00250 {
    00251     DKC_SINGLELIST *it = top;
    00252     size_t count = 0;
    00253     for(;it != NULL;)
    00254     {
    00255         count++;
    00256         it = it->mNext;
    00257     }
    00258     return count;
    00259 }
    00260
    00261 static DKC_SINGLELIST *dkcSingleListTail(DKC_SINGLELIST *top){
    00262     DKC_SINGLELIST *it = top;
    00263     for(;;)
    00264     {
    00265         if(NULL == it->mNext) break;
    00266         it = it->mNext;
    00267
    00268     }
    00269     return it;
    00270 }
    00271
    00272 //**********************************************************
    00273
    00274
    00275 static DKC_SINGLELIST *dkcSLOBeginLogic(struct dkc_SingleListObject *p){
    00276     //return p->mBegin->mNext;//beginには何も入っていないから。
    00277     return p->mBegin;
    00278 }
    00279 static DKC_SINGLELIST *dkcSLOTailLogic(struct dkc_SingleListObject *p){
    00280     return p->mTail;
    00281 }
    00282 static BOOL dkcSLOEndLogic(const DKC_SINGLELIST *p){
    00283     return (NULL==p);
    00284 }
    00285 static DKC_SINGLELIST *dkcSLONextLogic(const DKC_SINGLELIST *p){
    00286     return p->mNext;
    00287 }
    00288
    00289 static BOOL dkcSLOPushBackLogic(struct dkc_SingleListObject *p,const void *data,size_t size)
    00290 {
    00291     BOOL result;
    00292     result = DKUTIL_SUCCEEDED_BOOL(dkcSingleListInsert(p->mTail,data,size));
    00293     if(TRUE==result){//成功だ！
    00294         p->mTail = p->mTail->mNext;//tail更新
    00295     }
    00296     return result;
    00297 }
    00298 static void dkcSLOEraseLogic(struct dkc_SingleListObject *p,DKC_SINGLELIST *prev,DKC_SINGLELIST *target)
    00299 {
    00300     if(p->mTail == p->mBegin){
    00301         return;//何もない。
    00302     }else if(p->mTail == target){
    00303         prev->mNext = dkcSingleListErase(target);//多分NULLが返ってくる。
    00304         p->mTail = prev;//tail更新
    00305     }else if(p->mBegin == target){
    00306         prev->mNext = dkcSingleListErase(target);
    00307         p->mBegin = prev->mNext;//top 更新
    00308     }else{
    00309         prev->mNext = dkcSingleListErase(target);
    00310     }
    00311 }
    00312 static BOOL dkcSLOEmptyLogic(struct dkc_SingleListObject *p){
    00313     return (p->mBegin == p->mTail);
    00314 }
    00315
    00316 DKC_SINGLELIST_OBJECT *WINAPI dkcAllocSingleListObject(const void *data,size_t size){
    00317     DKC_SINGLELIST_OBJECT *p = NULL;
    00318
    00319     p = (DKC_SINGLELIST_OBJECT *)dkcAllocate(sizeof(DKC_SINGLELIST_OBJECT));
    00320     if(NULL==p) return NULL;
    00321
    00322
    00323     p->mBegin = dkcAllocSingleList(data,size);
    00324     if(NULL==p->mBegin) goto Error;
    00325     p->mTail = p->mBegin;
    00326
    00327
    00328     p->begin = dkcSLOBeginLogic;
    00329     p->tail = dkcSLOTailLogic;
    00330     p->end = dkcSLOEndLogic;
    00331     p->next = dkcSLONextLogic;
    00332
    00333     p->setbuffer = dkcSingleListSetBuffer;
    00334     p->getbuffer = dkcSingleListGetBuffer;
    00335     p->push_back = dkcSLOPushBackLogic;
    00336     p->erase = dkcSLOEraseLogic;
    00337
    00338     p->empty = dkcSLOEmptyLogic;
    00339
    00340
    00341
    00342     return p;
    00343 Error:
    00344     if(p){
    00345         dkcFreeSingleList(&p->mBegin);
    00346     }
    00347     dkcFree((void **)&p);
    00348     return NULL;
    00349 }
    00350
    00351 int WINAPI dkcFreeSingleListObject(DKC_SINGLELIST_OBJECT **p)
    00352 {
    00353     if(NULL==p || NULL==*p) return edk_ArgumentException;
    00354     dkcFreeSingleList(&(*p)->mBegin);
    00355     return dkcFree((void **)p);
    00356 }
    00357 /*
    00358 DKC_SINGLELIST_OBJECT * WINAPI dkcAllocSingleListObjectDeserialize(DKC_DESERIALIZE *se)
    00359 {
    00360     int sig;
    00361     size_t read;
    00362     DKC_SINGLELIST_OBJECT t,*plistobj;
    00363     DKC_SINGLELIST *li;
    00364
    00365     //シグネチャを取得
    00366     dkcDeserializeRead(se,&sig,sizeof(sig),&read);
    00367     //そんな馬鹿な！判定
    00368     if(read != sizeof(sig) || edkcSerializeIDSingleListObject != sig)
    00369     {
    00370         return NULL;
    00371     }
    00372     //objectを取得
    00373     dkcDeserializeRead(se,&t,sizeof(t),&read);
    00374
    00375     if(read != sizeof(t)){//なぜ、もう読み込めないのだ！
    00376         return NULL;
    00377     }
    00378     //single listを復元ナリ
    00379     li = dkcAllocSingleListDeserialize(se);
    00380     if(li == NULL) return NULL;
    00381
    00382     //objectをAlloc
    00383     plistobj = dkcAllocSingleListObject(NULL,0);
    00384 #   ifdef DEBUG
    00385     dkcmNOT_ASSERT(NULL== plistobj);
    00386 #   endif
    00387     if(NULL == plistobj) goto Error;
    00388
    00389     //内部のリストは解放しておく＾＾；結構強引な処理
    00390     dkcFreeSingleList(&plistobj->mBegin);
    00391
    00392     plistobj->mBegin = li;
    00393     plistobj->mTail = dkcSingleListTail(li);
    00394
    00395     //多分、これでOK!?
    00396     return plistobj;
    00397 Error:
    00398     dkcFreeSingleList(&li);
    00399     return NULL;
    00400 }
    00401
    00402
    00403
    00404 void WINAPI dkcSingleListObjectSerialize(const DKC_SINGLELIST_OBJECT *ptr,DKC_SERIALIZE *se)
    00405 {
    00406     int sig;
    00407
    00408     sig = edkcSerializeIDSingleListObject;
    00409     //シグネチャ保存
    00410     dkcSerializeWrite(se,&sig,sizeof(sig));
    00411     //objectを保存
    00412     dkcSerializeWrite(se,ptr,sizeof(DKC_SINGLELIST_OBJECT));
    00413
    00414     //シングルリストをシリアライズ
    00415     dkcSingleListSerialize(ptr->mBegin,se);
    00416 }
    00417
    00418 */