source: git/Singular/mmisc.c @ 551fd7

fieker-DuValspielwiese
Last change on this file since 551fd7 was 416465, checked in by Olaf Bachmann <obachman@…>, 25 years ago
* bug-fixes from work with Thomas git-svn-id: file:///usr/local/Singular/svn/trunk@3826 2c84dea3-7e68-4137-9b89-c4e89433aadc
  • Property mode set to 100644
File size: 13.9 KB
RevLine 
[52a5e8]1/****************************************
2*  Computer Algebra System SINGULAR     *
3****************************************/
[416465]4/* $Id: mmisc.c,v 1.22 1999-11-15 17:20:25 obachman Exp $ */
[52a5e8]5
6/*
7* ABSTRACT:
8*/
9
10#include "mod2.h"
11#include "mmemory.h"
12#include "mmprivate.h"
13#include "mmpage.h"
14#include "febase.h"
[c06a32]15#include "distrib.h"
[0f1252]16#include "tok.h"
[c06a32]17
[105efec]18#ifdef MTRACK
19#include "mmbt.h"
20#endif
[52a5e8]21
22static int mm_specSize = 0;
[b7b08c]23static memSpecHeap mm_SpecHeaps = NULL;
24static memSpecHeap mm_TempHeaps = NULL;
[52a5e8]25
[b7b08c]26memHeap mmGetSpecHeap( size_t size)
[52a5e8]27{
[b7b08c]28  int mm_new_specIndex = mmGetIndex( size );
29#ifdef ALIGN_8
30  if (size % 8 != 0) size = size + 8 - (size % 8);
31#endif
32  if (mm_new_specIndex < 0 || 
33      ((mm_theList[mm_new_specIndex].size != RealSizeFromSize(size)) && 
34       (SIZE_OF_HEAP_PAGE/RealSizeFromSize(size) 
35        > 
36        SIZE_OF_HEAP_PAGE/mm_theList[mm_new_specIndex].size)))
[52a5e8]37  {
[b7b08c]38    memSpecHeap s_heap;
39      s_heap
40        = mmFindInSortedGList(mm_SpecHeaps, 
[d6681d]41                              ((void*) &s_heap->next) - ((void*) s_heap), 
42                              ((void*) &s_heap->size) - ((void*) s_heap), 
[b7b08c]43                              RealSizeFromSize(size));
44    if (s_heap != NULL) 
[52a5e8]45    {
[b7b08c]46      (s_heap->ref)++;
47      assume(s_heap->heap != NULL && s_heap->heap->size == s_heap->size);
48      return s_heap->heap;
[52a5e8]49    }
[b7b08c]50    s_heap = (memSpecHeap) Alloc0SizeOf(ip_memSpecHeap);
51    s_heap->ref = 1;
52    s_heap->heap = mmCreateHeap(RealSizeFromSize(size));
53    s_heap->size = s_heap->heap->size;
54    mm_SpecHeaps = 
55      mmSortedInsertInGList(mm_SpecHeaps, 
[d6681d]56                            ((void*) &s_heap->next) - ((void*) s_heap), 
57                            ((void*) &s_heap->size) - ((void*) s_heap), 
[b7b08c]58                            s_heap);
59    return s_heap->heap;
60  }
61  else
62  {
63      return &(mm_theList[mm_new_specIndex]);
[52a5e8]64  }
65}
66
[b7b08c]67void mmUnGetSpecHeap(memHeap *heap_p)
[f62e786]68{
[b7b08c]69  memHeap heap = *heap_p;
70  int mm_this_specIndex = mmGetIndex(SizeFromRealSize(heap->size));
71
[9d06971]72/*  mmGarbageCollectHeap(heap, 0); */
[b7b08c]73
74  if (mm_this_specIndex < 0 || 
75      ((mm_theList[mm_this_specIndex].size != heap->size) && 
76       (SIZE_OF_HEAP_PAGE/heap->size) 
77        > 
78       (SIZE_OF_HEAP_PAGE/mm_theList[mm_this_specIndex].size)))
[f62e786]79  {
[b7b08c]80    memSpecHeap s_heap
81      = mmFindInSortedGList(mm_SpecHeaps, 
[d6681d]82                            ((void*) &s_heap->next) - ((void*) s_heap), 
83                            ((void*) &s_heap->size) - ((void*) s_heap), 
[b7b08c]84                            heap->size);
85    if (s_heap == NULL)
86    {
87#ifdef MDEBUG
88      fprintf(stderr, "Warning: mmUngetSpecHeap: heap not previously gotten with mmGetSpecHeap\n");
89#else
90      feReportBug("SpecHeap memory managment");
91#endif
92      return;
93    }
94    (s_heap->ref)--;
95    if (s_heap->ref == 0)
96    {
97      mm_SpecHeaps = 
98        mmRemoveFromGList(mm_SpecHeaps,
[d6681d]99                          ((void*) &s_heap->next) - ((void*) s_heap),
[b7b08c]100                          s_heap);
101      mmDestroyHeap(&(s_heap->heap));
102      FreeSizeOf(s_heap, ip_memSpecHeap);
103    }
[f62e786]104  }
[b7b08c]105  *heap_p = NULL;
106}
107 
108memHeap mmGetTempHeap(size_t size)
109{
110  memSpecHeap s_heap = (memSpecHeap) Alloc0SizeOf(ip_memSpecHeap);
111  s_heap->heap = mmCreateHeap(size);
112  mm_TempHeaps = 
113    mmSortedInsertInGList(mm_TempHeaps,
[d6681d]114                          ((void*) &s_heap->next) - ((void*) s_heap), 
115                          ((void*) &s_heap->size) - ((void*) s_heap), 
[b7b08c]116                          s_heap);
117  return s_heap->heap;
118}
119
120#ifndef HEAP_DEBUG
121void mmUnGetTempHeap(memHeap *heap_p) 
122#else
123void mmDebugUnGetTemHeap(memHeap *heap_p, char* file, int line)
124#endif
125{
126  memHeap heap = *heap_p;
127  memSpecHeap s_heap;
128  assume(heap != NULL);
129  s_heap = 
130    mmFindInSortedGList(mm_TempHeaps, 
[d6681d]131                        ((void*) &s_heap->next) - ((void*) s_heap), 
132                        ((void*) &s_heap->size) - ((void*) s_heap), 
[b7b08c]133                        heap->size);
134  if (s_heap == NULL)
[f62e786]135  {
[b7b08c]136#ifdef MDEBUG
137    fprintf(stderr, "Warning: mmUngetTempHeap: heap not previously gotten with mmGetTempHeap\n");
138#else
139    feReportBug("TempHeap memory managment");
140#endif
141    return;
[f62e786]142  }
[b7b08c]143  mm_TempHeaps = 
144    mmRemoveFromGList(mm_SpecHeaps,
[d6681d]145                      ((void*) &s_heap->next) - ((void*) s_heap),
[b7b08c]146                      s_heap);
147  mmDestroyHeap(&(s_heap->heap));
148  FreeSizeOf(s_heap, ip_memSpecHeap);
[f62e786]149}
150
[f983ed]151#ifndef HAVE_AUTOMATIC_GC
[b7b08c]152void mmGarbageCollectHeaps(int strict)
[52a5e8]153{
[0d44225]154#ifdef NDEBUG
[0f1252]155  int show_mem = BVERBOSE(V_SHOW_MEM);
[b7b08c]156  int i;
157  int s_strict = strict & 1;
158  memSpecHeap s_heap;
159  s_heap = mm_SpecHeaps;
[0f1252]160 
161  if (show_mem)
162  {
163    fprintf(stdout, "[%dk]:{%dk}gc", 
164            (mm_bytesValloc + mm_bytesMalloc + 1023)/1024,
165            (mmMemUsed()+1023)/1024);
166    fflush(stdout);
167    verbose &= ~Sy_bit(V_SHOW_MEM);
168  }
[942846]169 
[b7b08c]170  while (s_heap != NULL)
171  {
172    mmGarbageCollectHeap(s_heap->heap, s_strict);
173    s_heap = s_heap->next;
174  }
[942846]175  if (strict & 4)
[b7b08c]176  {
177    s_heap = mm_TempHeaps;
178    while (s_heap != NULL)
179    {
180      mmGarbageCollectHeap(s_heap->heap, s_strict);
181      s_heap = s_heap->next;
182    }
183  }
184  for (i=0; mmGetSize(i) <= MAX_BLOCK_SIZE; i++)
185  {
186    mmGarbageCollectHeap(&mm_theList[i], s_strict);
187  }
188  if (strict & 2) mmReleaseFreePages();
[0f1252]189  if (show_mem)
190  {
191    fprintf(stdout, "[%dk]:{%dk}", 
192            (mm_bytesValloc + mm_bytesMalloc + 1023)/1024,
193            (mmMemUsed()+1023)/1024);
194    fflush(stdout);
195    verbose |= Sy_bit(V_SHOW_MEM);
196  }
[0d44225]197#endif
[52a5e8]198}
[f983ed]199#endif
[b7b08c]200 
[52a5e8]201size_t mmSizeL( void* adr )
202{
203  if (adr!=NULL)
204  {
205    adr = (size_t*)adr-1;
206    return *(size_t*)adr;
207  }
208  return 0;
209}
210
211int mmMemAlloc( void )
212{
213  return mm_bytesMalloc + mm_bytesValloc;
214}
[b7b08c]215
[52a5e8]216int mmMemUsed( void )
217{
218  int bytesfree = 0;
219  int i;
[b7b08c]220  memSpecHeap s_heap;
[52a5e8]221
[f983ed]222#ifndef HAVE_AUTOMATIC_GC
[b7b08c]223  for (i=0; mmGetSize(i) <= MAX_BLOCK_SIZE; i++)
[52a5e8]224    bytesfree += mmListLength(mm_theList[i].current)*mm_theList[i].size;
[b7b08c]225
226  s_heap = mm_SpecHeaps;
227  while (s_heap != NULL)
228  {
229    bytesfree += mmListLength(s_heap->heap->current) * (s_heap->heap->size);
230    s_heap = s_heap->next;
231  }
232  s_heap = mm_TempHeaps;
233  while (s_heap != NULL)
234  {
235    bytesfree += mmListLength(s_heap->heap->current) * s_heap->heap->size;
236    s_heap = s_heap->next;
237  }
[f983ed]238#endif
[52a5e8]239  return
[b7b08c]240    mm_bytesMalloc + mm_bytesValloc
241     - bytesfree - mmGetNumberOfFreePages()*SIZE_OF_PAGE;
[52a5e8]242}
243
244#ifdef HAVE_SBRK
245#include <unistd.h>
246int mmMemPhysical( void )
247{
248  unsigned long ns = (unsigned long) sbrk(0);
249  return (ns >=  mm_SbrkInit ? ns - mm_SbrkInit : mm_SbrkInit - ns);
250}
251#endif
252
253
254int mm_bytesMalloc=0;
[b7b08c]255int mm_bytesValloc = 0;
[52a5e8]256static int mm_printMark=102400;
257
258#ifndef ABS
259#define ABS(x) ((x)<0?(-(x)):(x))
260#endif
261
262void mmCheckPrint( void )
263{
264  int mm_bytesAlloc = mm_bytesValloc + mm_bytesMalloc;
[393d6b]265
[942846]266#if 0
[52a5e8]267  if ( ABS(mm_bytesAlloc - mm_printMark)>(100*1024) )
268  {
269    int i=(mm_bytesAlloc+1023)/1024;
270    fprintf( stdout, "[%dk]", i);
271    fflush( stdout );
272    mm_printMark=mm_bytesAlloc;
273  }
[942846]274#else
275  if ( ABS(mm_bytesAlloc - mm_printMark)>(1000*1024) )
276  {
277    mmPrintStat();
278    mm_printMark=mm_bytesAlloc;
279  }
280#endif
[52a5e8]281}
282
[b7b08c]283extern memHeap mm_specHeap;
284
[d6681d]285extern int mmNumberOfAllocatedHeapPages(memHeap heap);
286extern int mmNumberOfFreeHeapBlocks(memHeap heap);
287
[b7b08c]288static void mmPrintHeapStat(memHeap heap, int i)
289{
290  long l,a;
291  if (i >= 0) printf("%d", i);
292  else if (i== -1) printf("S");
293  else if (i== -2) printf("T");
294  printf("\t%ld", heap->size);
[d6681d]295  a = mmNumberOfFreeHeapBlocks(heap);
[b7b08c]296  if (heap->size > MAX_HEAP_CHUNK_SIZE)
297  {
[d6681d]298#ifndef HAVE_AUTOMATIC_GC
[b7b08c]299    l = (int) heap->pages;
300    printf("\t%ld\t%d\t%ld\t%ld",
301           l, (l > 0 ? ((int) ((1.0 -
302                                ((double) a)
303                                /
304                                ((double) l)
305                                )*100.0))
306               : 0), a, l-a);
[d6681d]307#endif
[b7b08c]308  }
309  else
310  {
[d6681d]311    l = mmNumberOfAllocatedHeapPages(heap);
[b7b08c]312    printf("\t%ld\t%d\t%ld\t%ld",
313           l,
314           (l != 0 ? ((int) ((1.0 -
315                              ((double) a)
316                              /
[d6681d]317                              ((double) l*(SIZE_OF_HEAP_PAGE/heap->size))
[b7b08c]318                              )*100.0))
319            : 0),
320           a,
[d6681d]321           l*(SIZE_OF_HEAP_PAGE/heap->size) - a);
[b7b08c]322  }
323  if (heap == mm_specHeap) printf(" *");
324  else if (mm_specHeap != NULL && mm_specHeap->size == heap->size)
325    printf(" +");
326  printf("\n");
327  fflush(stdout);
328}
329     
[52a5e8]330void mmPrintStat()
331{
[726d50]332#ifndef MAKE_DISTRIBUTION
[393d6b]333  int i;
334  long l,a;
[b7b08c]335  memSpecHeap s_heap;
[d6681d]336 
337  mmTestHeaps();
[393d6b]338#ifdef HAVE_SBRK
[52a5e8]339  printf("Physical:%dk ", (mmMemPhysical()+ 1023)/1024);
[393d6b]340#endif
[52a5e8]341  printf("Alloc:%dk ", (mmMemAlloc() + 1023)/1024);
342  printf("Used:%dk ", (mmMemUsed()+ 1023)/1024);
343  printf("Malloc:%dk ", (mm_bytesMalloc+ 1023)/1024);
344  printf("Valloc:%dk ", (mm_bytesValloc+ 1023)/1024);
345  printf("Palloc:%d ", mmGetNumberOfAllocatedPages());
346  printf("Pused:%d ", mmGetNumberOfUsedPages());
347  printf("\n");
348
349  printf("Heap\tSize\tPages\tUsage\tFree\tUsed\n");
[b7b08c]350  for (i=0; mmGetSize(i) <= MAX_BLOCK_SIZE; i++)
[52a5e8]351  {
[b7b08c]352    mmPrintHeapStat(&(mm_theList[i]), i);
353  }
354  s_heap = mm_SpecHeaps;
355  while (s_heap != NULL)
356  {
357    mmPrintHeapStat(s_heap->heap, -1);
358    s_heap = s_heap->next;
359  }
360  s_heap = mm_TempHeaps;
361  while (s_heap != NULL)
362  {
363    mmPrintHeapStat(s_heap->heap, -2);
364    s_heap = s_heap->next;
[52a5e8]365  }
366#endif
[726d50]367}
[52a5e8]368
[7df2ef]369#ifdef MLIST
[5c187b]370void mmTestList (FILE *fd, int all)
[7df2ef]371{
372  DBMCB * what=mm_theDBused.next;
[5c187b]373  fprintf(fd,"list of used blocks:\n");
[7df2ef]374  while (what!=NULL)
375  {
[e56c23]376    if ((all & MM_PRINT_ALL_ADDR) || ! (what->flags & MM_INITFLAG))
[6e5833]377    {
[5c187b]378      fprintf( fd, "%d bytes at %p allocated in: %s:%d",
[a5afbf]379               (int)what->size, what, what->allocated_fname, what->allocated_lineno);
[105efec]380#ifdef MTRACK
[5c187b]381      mmDBPrintStack(fd, what, all);
[105efec]382#else
[5c187b]383      fprintf( fd, "\n");
[105efec]384#endif
[6e5833]385    }
[7df2ef]386    what=what->next;
387  }
388}
389#endif
390
[d6681d]391#ifdef HEAP_DEBUG
392int mmTestHeaps()
393{
394  int i = -1;
395
396  do
397  {
398    i++;
399    if (! mmCheckHeap(&mm_theList[i])) return 0;
400  }
401  while (mmGetSize(i) < MAX_BLOCK_SIZE);
402
403  return 1;
404}
405#endif
406
[52a5e8]407
408/**********************************************************************
409 *
[393d6b]410 * Some operations on linked lists of memory
[52a5e8]411 *
412 **********************************************************************/
413
[f8519e]414void* mmRemoveFromList(void* list, void* element)
415{
416  void* nlist;
417  void* olist;
[393d6b]418
[f8519e]419  if (list == NULL) return NULL;
420
421  nlist = *((void**) list);
422  olist = list;
[393d6b]423
[f8519e]424  if (list == element) return nlist;
[393d6b]425
[f8519e]426  while (nlist != NULL && nlist != element)
427  {
428    list = nlist;
429    nlist = *((void**) list);
430  }
[393d6b]431
[f8519e]432  if (nlist != NULL) *((void**) list) = *((void**) nlist);
[393d6b]433
[f8519e]434  return olist;
435}
436
[52a5e8]437int mmListLength(void* list)
438{
439  int l = 0;
440  while (list != NULL)
441  {
442    l++;
443    list = *((void**) list);
444  }
445  return l;
446}
447
448void* mmListLast(void* memList)
449{
450  if (memList == NULL) return NULL;
451
452  while (*((void**) memList) != NULL)
453    memList = *((void**) memList);
454
455  return memList;
456}
457
458int mmIsAddrOnList(void* addr, void* list)
459{
460  if (addr == NULL)
461    return (list == NULL);
[393d6b]462
[52a5e8]463  while (list != NULL)
464  {
465    if (addr == list) return 1;
466    list = *((void**) list);
467  }
468  return 0;
469}
470
471void* mmListHasCycle(void* list)
472{
473  void* l1 = list;
474  void* l2;
[393d6b]475
[52a5e8]476  int l = 0, i;
477
478  while (l1 != NULL)
479  {
480    i = 0;
481    l2 = list;
482    while (l1 != l2)
483    {
484      i++;
485      l2 = *((void**) l2);
486    }
487    if (i != l) return l1;
488    l1 = *((void**) l1);
489    l++;
490  }
491  return NULL;
492}
[393d6b]493
[52a5e8]494
495int mmGListLength(void* list, int next)
496{
497  int l = 0;
498  while (list != NULL)
499  {
500    l++;
[d6681d]501    list = *((void**) (list + next));
[52a5e8]502  }
503  return l;
504}
505
506void* mmGListLast(void* memList, int next)
507{
508  if (memList == NULL) return NULL;
509
510  while (*((void**) memList) != NULL)
[d6681d]511    memList = *((void**) (memList + next));
[52a5e8]512
513  return memList;
514}
515
516int mmIsAddrOnGList(void* addr, void* list, int next)
517{
518  if (addr == NULL)
519    return (list == NULL);
[393d6b]520
[52a5e8]521  while (list != NULL)
522  {
523    if (addr == list) return 1;
[d6681d]524    list = *((void**) (list + next));
[52a5e8]525  }
526  return 0;
527}
528
529void* mmGListHasCycle(void* list, int next)
530{
531  void* l1 = list;
532  void* l2;
[393d6b]533
[52a5e8]534  int l = 0, i;
535
536  while (l1 != NULL)
537  {
538    i = 0;
539    l2 = list;
540    while (l1 != l2)
541    {
542      i++;
543      l2 = *((void**) (l2 + next));
544    }
545    if (i != l) return l1;
546    l1 = *((void**) (l1 + next));
547    l++;
548  }
549  return NULL;
550}
551
[b7b08c]552void* mmSortedInsertInGList(void* list, int next, int int_field, void* element)
553{
[d6681d]554  int el_size = *((int *) ((void**)(element + int_field)));
[b7b08c]555 
[d6681d]556  if (list == NULL || *((int *)((void**)(list + int_field))) > el_size)
[b7b08c]557  {
[d6681d]558    *((void**)(element + next)) = list;
[b7b08c]559    return element;
560  }
561  else
562  {
563    void* prev = list;
[d6681d]564    void* curr = *((void**)(list + next));
[b7b08c]565   
[d6681d]566    while (curr != NULL && *((int *)((void**)(curr + int_field))) > el_size)
[b7b08c]567    {
568      prev = curr;
[d6681d]569      curr = *((void**)(curr + next));
[b7b08c]570    }
571    assume(prev != NULL);
[d6681d]572    *((void**)(prev+ next)) = element;
573    *((void**)(element+ next)) = curr;
[b7b08c]574    return list;
575  }
576}
577
578void* mmFindInSortedGList(void* list, int next, int int_field, int what)
579{
580  while (1)
581  {
[d6681d]582    if (list == NULL || *((int *)((void**) (list + int_field))) > what)
[b7b08c]583      return NULL;
[d6681d]584    if (*((int *)((void**)(list + int_field))) == what) return list;
585    list = *((void**) (list + next));
[b7b08c]586  }
587}
588
589void* mmRemoveFromGList(void* list, int next, void* element)
590{
591  void* nlist;
592  void* olist;
593
594  if (list == NULL) return NULL;
595
596  nlist = *((void**) (list + next));
597  olist = list;
598
599  if (list == element) return nlist;
600
601  while (nlist != NULL && nlist != element)
602  {
603    list = nlist;
604    nlist = *((void**) (list + next));
605  }
606
607  if (nlist != NULL) *((void**) (list + next)) = *((void**) (nlist + next));
608
609  return olist;
610}
611
[52a5e8]612/**********************************************************************
613 *
614 * Operations for deep profiles
615 *
616 **********************************************************************/
617
618#ifdef DO_DEEP_PROFILE
[a5c76f]619void _memcpyW(long* p1, long* p2, long l)
[52a5e8]620{
621  assume(l >= 0);
622
623  while(l)
624  {
625    *p1++ = *p2++;
626    l--;
627  }
628}
629
[a5c76f]630void _memaddW(long* p1, long* p2, long* p3, long l)
[52a5e8]631{
632  assume(l >= 0);
[393d6b]633
[52a5e8]634  while (l)
635  {
636    *p1++ = *p2++ + *p3++;
637    l--;
638  }
639}
640
[a5c76f]641void _memsetW(long* p1, long w, long l)
[52a5e8]642{
643  assume(l >= 0);
[393d6b]644
[52a5e8]645  while (l)
646  {
647    *p1++ = w;
648    l--;
649  }
650}
651
652#endif /* DO_DEEP_PROFILE */
653
654#ifdef sun
655#ifdef __svr4__
656void bzero(char *s,int n)
657{
658  memset(s,0,n);
659}
660#endif
661#endif
Note: See TracBrowser for help on using the repository browser.