Mercurial > cgi-bin > hgwebdir.cgi > VMS > C_Libraries > Queue_impl
changeset 18:7c9e00ff1bf4 VMS__malloc_brch
fixed queue enlarging function
| author | Merten Sach <msach@mailbox.tu-berlin.de> |
|---|---|
| date | Wed, 22 Jun 2011 18:49:17 +0200 |
| parents | 1e93e5dbeda1 |
| children | 677afc259a58 |
| files | PrivateQueue.c |
| diffstat | 1 files changed, 54 insertions(+), 49 deletions(-) [+] |
line diff
1.1 --- a/PrivateQueue.c Wed Jun 22 16:55:10 2011 +0200 1.2 +++ b/PrivateQueue.c Wed Jun 22 18:49:17 2011 +0200 1.3 @@ -39,18 +39,23 @@ 1.4 1.5 void 1.6 enlargePrivQ( PrivQueueStruc *Q ) 1.7 - { int oldSize, newSize; 1.8 + { size_t oldSize, newSize; 1.9 void **oldStartOfData; 1.10 1.11 - oldSize = Q->endOfData - Q->startOfData; 1.12 + oldSize = Q->endOfData - Q->startOfData + 1; 1.13 newSize = 2 * oldSize; 1.14 oldStartOfData = Q->startOfData; 1.15 - Q->startOfData = VMS__malloc( newSize * sizeof(void *) ); 1.16 - memcpy(Q->startOfData, oldStartOfData, oldSize * sizeof(void *)); 1.17 + Q->startOfData = VMS__malloc( newSize * sizeof(void*)); 1.18 + //copy second half 1.19 + size_t secondHalfSize = Q->endOfData - Q->extractPos + 1; 1.20 + memcpy(Q->startOfData,Q->extractPos, secondHalfSize * sizeof(void*)); 1.21 + //copy first half 1.22 + memcpy(Q->startOfData + secondHalfSize, oldStartOfData, 1.23 + (oldSize-secondHalfSize) * sizeof(void*)); 1.24 VMS__free(oldStartOfData); 1.25 1.26 - Q->extractPos = &(Q->startOfData[0]); //side by side == empty 1.27 - Q->insertPos = &(Q->startOfData[1]); // so start pos's have to be 1.28 + Q->extractPos = Q->startOfData; 1.29 + Q->insertPos = Q->startOfData + oldSize - 1; 1.30 Q->endOfData = &(Q->startOfData[newSize - 1]); 1.31 } 1.32 1.33 @@ -106,28 +111,28 @@ 1.34 void 1.35 writePrivQ( void * in, PrivQueueStruc* Q ) 1.36 { 1.37 - void **startOfData = Q->startOfData; 1.38 - void **endOfData = Q->endOfData; 1.39 - 1.40 - void **insertPos = Q->insertPos; 1.41 - void **extractPos = Q->extractPos; 1.42 + while(1){ 1.43 + void **startOfData = Q->startOfData; 1.44 + void **endOfData = Q->endOfData; 1.45 1.46 -tryAgain: 1.47 - //Full? (insert is just below extract when full) 1.48 - if( extractPos - insertPos != 1 && 1.49 - !(insertPos == endOfData && extractPos == startOfData)) 1.50 - { *(Q->insertPos) = in; //insert before move 1.51 - if( insertPos == endOfData ) //write new pos exactly once, correctly 1.52 - { Q->insertPos = startOfData; 1.53 - } 1.54 - else 1.55 - { Q->insertPos++; 1.56 - } 1.57 - return; 1.58 - } 1.59 - //Q is full 1.60 - enlargePrivQ( Q ); 1.61 - goto tryAgain; 1.62 + void **insertPos = Q->insertPos; 1.63 + void **extractPos = Q->extractPos; 1.64 + 1.65 + //Full? (insert is just below extract when full) 1.66 + if( extractPos - insertPos != 1 && 1.67 + !(insertPos == endOfData && extractPos == startOfData)) 1.68 + { *(Q->insertPos) = in; //insert before move 1.69 + if( insertPos == endOfData ) //write new pos exactly once, correctly 1.70 + { Q->insertPos = startOfData; 1.71 + } 1.72 + else 1.73 + { Q->insertPos++; 1.74 + } 1.75 + return; 1.76 + } 1.77 + //Q is full 1.78 + enlargePrivQ( Q ); 1.79 + } 1.80 } 1.81 1.82 1.83 @@ -164,30 +169,30 @@ 1.84 void 1.85 pushPrivQ( void * in, PrivQueueStruc* Q ) 1.86 { 1.87 - void **startOfData = Q->startOfData; 1.88 - void **endOfData = Q->endOfData; 1.89 + while(1){ 1.90 + void **startOfData = Q->startOfData; 1.91 + void **endOfData = Q->endOfData; 1.92 1.93 - void **insertPos = Q->insertPos; 1.94 - void **extractPos = Q->extractPos; 1.95 + void **insertPos = Q->insertPos; 1.96 + void **extractPos = Q->extractPos; 1.97 1.98 -tryAgain: 1.99 - //Full? (insert is just below extract when full) 1.100 - if( extractPos - insertPos != 1 && 1.101 - !(insertPos == endOfData && extractPos == startOfData)) 1.102 - { //insert -- but go backwards, inserting at read position then 1.103 - // move read pos backwards 1.104 - *(Q->extractPos) = in; 1.105 - if( extractPos == startOfData ) //write new pos exactly once, correctly 1.106 - { Q->extractPos = endOfData; //can't overrun then fix it 'cause 1.107 - } // other thread might read bad pos 1.108 - else 1.109 - { Q->extractPos--; 1.110 - } 1.111 - return; 1.112 - } 1.113 - //Q is full 1.114 - enlargePrivQ( Q ); 1.115 - goto tryAgain; 1.116 + //Full? (insert is just below extract when full) 1.117 + if( extractPos - insertPos != 1 && 1.118 + !(insertPos == endOfData && extractPos == startOfData)) 1.119 + { //insert -- but go backwards, inserting at read position then 1.120 + // move read pos backwards 1.121 + *(Q->extractPos) = in; 1.122 + if( extractPos == startOfData ) //write new pos exactly once, correctly 1.123 + { Q->extractPos = endOfData; //can't overrun then fix it 'cause 1.124 + } // other thread might read bad pos 1.125 + else 1.126 + { Q->extractPos--; 1.127 + } 1.128 + return; 1.129 + } 1.130 + //Q is full 1.131 + enlargePrivQ( Q ); 1.132 + } 1.133 } 1.134 1.135 void
