links

lynx-like text mode web browser
git clone anongit@rnpnr.xyz:links.git
Log | Files | Refs | Feed | README | LICENSE

memory.c (1649B)


      1 /* memory.c
      2  * (c) 2002 Mikulas Patocka
      3  * This file is a part of the Links program, released under GPL.
      4  */
      5 
      6 #include "links.h"
      7 
      8 struct cache_upcall {
      9 	list_entry_1st;
     10 	int (*upcall)(int);
     11 	unsigned char flags;
     12 	unsigned char name[1];
     13 };
     14 
     15 static struct list_head cache_upcalls = { &cache_upcalls,
     16 	                                  &cache_upcalls }; /* cache_upcall */
     17 
     18 int
     19 shrink_memory(int type)
     20 {
     21 	struct cache_upcall *c = NULL;
     22 	struct list_head *lc;
     23 	int a = 0;
     24 	foreach (struct cache_upcall, c, lc, cache_upcalls) {
     25 		a |= c->upcall(type);
     26 	}
     27 	return a;
     28 }
     29 
     30 void
     31 register_cache_upcall(int (*upcall)(int), int flags, unsigned char *name)
     32 {
     33 	struct cache_upcall *c;
     34 	c = xmalloc(sizeof(struct cache_upcall) + strlen(cast_const_char name));
     35 	c->upcall = upcall;
     36 	c->flags = (unsigned char)flags;
     37 	strcpy(cast_char c->name, cast_const_char name);
     38 	add_to_list(cache_upcalls, c);
     39 }
     40 
     41 void
     42 free_all_caches(void)
     43 {
     44 	struct cache_upcall *c = NULL;
     45 	struct list_head *lc;
     46 	int a, b;
     47 	do {
     48 		a = 0;
     49 		b = ~0;
     50 		foreach (struct cache_upcall, c, lc, cache_upcalls) {
     51 			int x = c->upcall(SH_FREE_ALL);
     52 			a |= x;
     53 			b &= x;
     54 		}
     55 	} while (a & ST_SOMETHING_FREED);
     56 	if (!(b & ST_CACHE_EMPTY)) {
     57 		unsigned char *m = NULL;
     58 		size_t l = 0;
     59 		foreach (struct cache_upcall, c, lc, cache_upcalls)
     60 			if (!(c->upcall(SH_FREE_ALL) & ST_CACHE_EMPTY)) {
     61 				if (l)
     62 					l = add_to_str(&m, l, cast_uchar ", ");
     63 				l = add_to_str(&m, l, c->name);
     64 			}
     65 		internal("could not release entries from caches: %s", m);
     66 		free(m);
     67 	}
     68 	free_list(struct cache_upcall, cache_upcalls);
     69 }
     70 
     71 int
     72 out_of_memory(void)
     73 {
     74 	if (shrink_memory(SH_FREE_SOMETHING))
     75 		return 1;
     76 
     77 	return 0;
     78 }