STATIC void calcAggregates( void ) /********************************/ { unsigned index; unsigned index2; int cmp_result; unsigned *sorted_idx; address ***sorted_vect; massgd_sample_addr **massgd_data; // unsigned mbuckets; unsigned curr_mbucket; unsigned curr_midx; thread_data *thd; unsigned buckets; unsigned base; unsigned best; unsigned end; massgd_sample_addr *curr; ClearMassaged( CurrSIOData ); buckets = 0; for( thd = CurrSIOData->samples; thd != NULL; thd = thd->next ) { buckets += RAW_BUCKET_IDX( thd->end_time - thd->start_time ) + 1; } sorted_idx = ProfCAlloc( buckets * sizeof( *sorted_idx ) ); sorted_vect = ProfAlloc( buckets * sizeof(*thd->raw_bucket) ); base = 0; for( thd = CurrSIOData->samples; thd != NULL; thd = thd->next ) { end = RAW_BUCKET_IDX( thd->end_time - thd->start_time ) + 1; for( index = 0; index < end; ++index, ++base ) { sorted_vect[base] = ProfAlloc( MAX_RAW_BUCKET_INDEX * sizeof( **sorted_vect ) ); for( index2 = 0; index2 < MAX_RAW_BUCKET_INDEX; ++index2 ) { sorted_vect[base][index2] = &thd->raw_bucket[index][index2]; } qsort( sorted_vect[base], MAX_RAW_BUCKET_INDEX, sizeof(**sorted_vect), rawSampCmp ); } } /* skip over all the 0:0 samples */ for( index = 0; index < buckets; ++index ) { index2 = 0; for( ;; ) { if( index2 >= MAX_RAW_BUCKET_INDEX ) break; if( !(sorted_vect[index][index2]->mach.segment == 0 && sorted_vect[index][index2]->mach.offset == 0) ) break; ++index2; } sorted_idx[index] = index2; } curr = NULL; curr_mbucket = 0; curr_midx = -1; // mbuckets = 1; massgd_data = ProfAlloc( sizeof( *massgd_data ) ); massgd_data[0] = ProfCAlloc( MAX_MASSGD_BUCKET_SIZE ); for( ;; ) { best = -1U; for( index = 0; index < buckets; ++index ) { index2 = sorted_idx[index]; if( index2 >= MAX_RAW_BUCKET_INDEX ) continue; if( best == -1U ) best = index; cmp_result = AddrCmp( sorted_vect[index][index2], sorted_vect[best][sorted_idx[best]] ); if( cmp_result < 0 ) best = index; } if( best == -1U ) break; if( curr == NULL || AddrCmp( sorted_vect[best][sorted_idx[best]], curr->raw ) != 0 ) { if( ++curr_midx >= MAX_MASSGD_BUCKET_INDEX ) { ++curr_mbucket; massgd_data = ProfRealloc( massgd_data, (curr_mbucket+1) * sizeof(*massgd_data) ); massgd_data[curr_mbucket] = ProfCAlloc( MAX_MASSGD_BUCKET_SIZE ); curr_midx = 0; } curr = &massgd_data[curr_mbucket][curr_midx]; curr->raw = sorted_vect[best][sorted_idx[best]]; } curr->hits++; sorted_idx[best]++; } CurrSIOData->massaged_sample = massgd_data; CurrSIOData->number_massaged = 1 + curr_midx + (curr_mbucket * (unsigned long)MAX_MASSGD_BUCKET_INDEX); CurrSIOData->massaged_mapped = true; for( index = 0; index < buckets; ++index ) { ProfFree( sorted_vect[index] ); } ProfFree( sorted_vect ); ProfFree( sorted_idx ); }
STATIC bool procSampleBlock( clicks_t tick, uint_16 total_len, samp_data *data ) /*************************************************************/ { thread_id thread; unsigned data_index; unsigned index; unsigned index2; unsigned count; unsigned buckets; clicks_t end_tick; ldiv_t div_result; thread_data *thd; thread_data **owner; address *samp; thread = data->sample.thread_id; total_len -= offsetof( samp_block, d.sample ); count = total_len / sizeof( samp_address ); CurrSIOData->total_samples += count; end_tick = tick + count; owner = &CurrSIOData->samples; for( ;; ) { thd = *owner; if( thd == NULL ) { thd = ProfAlloc( sizeof( *thd ) ); *owner = thd; thd->next = NULL; thd->thread = thread; thd->start_time = tick; thd->end_time = end_tick; buckets = RAW_BUCKET_IDX( count ) + 1; thd->raw_bucket = ProfAlloc( buckets * sizeof( *thd->raw_bucket ) ); for( index = 0; index < buckets; ++index ) { thd->raw_bucket[index] = ProfCAlloc( MAX_RAW_BUCKET_SIZE ); } break; } if( thd->thread == thread ) break; owner = &thd->next; } if( end_tick > thd->end_time ) { index = RAW_BUCKET_IDX( thd->end_time - thd->start_time ) + 1; buckets = RAW_BUCKET_IDX( end_tick - thd->start_time ) + 1; if( buckets > index ) { thd->raw_bucket = ProfRealloc( thd->raw_bucket, buckets * sizeof( *thd->raw_bucket ) ); for( ; index < buckets; ++index ) { thd->raw_bucket[index] = ProfCAlloc( MAX_RAW_BUCKET_SIZE ); } } thd->end_time = end_tick; } div_result = ldiv( tick - thd->start_time, MAX_RAW_BUCKET_INDEX ); index = div_result.quot; index2 = div_result.rem; data_index = 0; while( count > 0 ) { samp = &thd->raw_bucket[index][index2]; samp->mach.segment = data->sample.sample[data_index].segment; samp->mach.offset = data->sample.sample[data_index].offset; if( ++index2 >= MAX_RAW_BUCKET_INDEX ) { index2 = 0; ++index; } ++data_index; --count; } return( true ); }