Remove many valgrind-detected memory leaks. - sam - An updated version of the sam text editor.
(HTM) git clone git://vernunftzentrum.de/sam.git
(DIR) Log
(DIR) Files
(DIR) Refs
(DIR) LICENSE
---
(DIR) commit 3a8f45f007849613466d20ed16760917bdb2bf9d
(DIR) parent 569a1de5d7884bad2b30e9a2b5280a941ed228cf
(HTM) Author: Rob King <jking@deadpixi.com>
Date: Thu, 20 Oct 2016 15:55:35 -0500
Remove many valgrind-detected memory leaks.
Diffstat:
sam/buffer.c | 3 ++-
sam/cmd.c | 46 +++++++++++++++++++++++++------
sam/error.c | 2 ++
sam/file.c | 16 +++++++++++++++-
sam/mesg.c | 3 ++-
sam/multi.c | 3 ++-
sam/sam.c | 50 ++++++++++++++++++++++++++-----
sam/sam.h | 5 ++++-
sam/unix.c | 13 ++++---------
9 files changed, 110 insertions(+), 31 deletions(-)
---
(DIR) diff --git a/sam/buffer.c b/sam/buffer.c
@@ -124,13 +124,14 @@ Bterm(Buffer *b)
}
}
+/* XXX - modify at call sites to use the internal functions */
int
Bread(Buffer *b, wchar_t *c, int l, Posn p)
{
if (p + l > b->nrunes)
l = b->nrunes - p;
- if (l == 0)
+ if (l <= 0)
return 0;
size_t r = readbuffer(b->gb, p, l, c);
(DIR) diff --git a/sam/cmd.c b/sam/cmd.c
@@ -59,6 +59,22 @@ List stringlist;
bool eof;
void
+freecmdlists(void)
+{
+ if (cmdlist.listptr)
+ free(cmdlist.listptr);
+
+ if (addrlist.listptr)
+ free(addrlist.listptr);
+
+ if (relist.listptr)
+ free(relist.listptr);
+
+ if (stringlist.listptr)
+ free(stringlist.listptr);
+}
+
+void
resetcmd(void)
{
linep = line;
@@ -71,8 +87,8 @@ int
inputc(void)
{
int n, nbuf;
- char buf[3];
- wchar_t r;
+ char buf[3] = {0};
+ wchar_t r = 0;
Again:
nbuf = 0;
@@ -203,7 +219,7 @@ cmdloop(void)
for(;;){
if(!downloaded && curfile && curfile->state==Unread)
load(curfile);
- if((cmdp = parsecmd(0))==0){
+ if((cmdp = parsecmd(0)) == NULL){
if(downloaded){
rescue();
exit(EXIT_FAILURE);
@@ -212,8 +228,10 @@ cmdloop(void)
}
ocurfile = curfile;
loaded = curfile && curfile->state!=Unread;
- if(cmdexec(curfile, cmdp) == 0)
+ if(cmdexec(curfile, cmdp) == 0){
+ freecmd();
break;
+ }
freecmd();
cmdupdate();
update();
@@ -274,8 +292,12 @@ freecmd(void)
{
int i;
- while(cmdlist.nused > 0)
- free(cmdlist.uint8_tpptr[--cmdlist.nused]);
+ while(cmdlist.nused > 0){
+ Cmd *c = (Cmd *)cmdlist.uint8_tpptr[--cmdlist.nused];
+ /* XXX if (c->ctext)
+ free(c->ctext); */
+ free(c);
+ }
while(addrlist.nused > 0)
free(addrlist.uint8_tpptr[--addrlist.nused]);
while(relist.nused > 0){
@@ -426,6 +448,8 @@ parsecmd(int nest)
okdelim(c);
cmd.re = getregexp(c);
if(ct->cmdc == 's'){
+ if (cmd.ctext)
+ free(cmd.ctext);
cmd.ctext = newstring();
getrhs(cmd.ctext, c, 's');
if(nextc() == c){
@@ -446,11 +470,15 @@ parsecmd(int nest)
cmd.ccmd->cmdc = ct->defcmd;
}else if((cmd.ccmd = parsecmd(nest))==0)
panic("defcmd");
- }else if(ct->text)
+ } else if(ct->text){
+ if (cmd.ctext)
+ free(cmd.ctext);
cmd.ctext = collecttext();
- else if(ct->token)
+ } else if(ct->token){
+ if (cmd.ctext)
+ free(cmd.ctext);
cmd.ctext = collecttoken(ct->token);
- else
+ } else
atnl();
}else
switch(cmd.cmdc){
(DIR) diff --git a/sam/error.c b/sam/error.c
@@ -128,6 +128,8 @@ termwrite(char *s)
else
Strinsert(&cmdstr, p, cmdstr.n);
cmdptadv += p->n;
+ Strclose(p);
+ free(p);
}else
Write(STDERR_FILENO, s, strlen(s));
}
(DIR) diff --git a/sam/file.c b/sam/file.c
@@ -1,5 +1,6 @@
/* Copyright (c) 1998 Lucent Technologies - All rights reserved. */
#include "sam.h"
+
/*
* Files are splayed out a factor of NDISC to reduce indirect block access
*/
@@ -19,12 +20,22 @@ enum{
MAXCACHE=STRSIZE /* max length of cache. must be < 32K-BLOCKSIZE */
};
+static void
+freebufs(void)
+{
+ Bterm(undobuf);
+ Bterm(snarfbuf);
+ Bterm(plan9buf);
+}
+
void
Fstart(void)
{
undobuf = Bopen();
snarfbuf = Bopen();
plan9buf = Bopen();
+
+ atexit(freebufs);
}
void
@@ -75,8 +86,11 @@ Fopen(void)
void
Fclose(File *f)
{
+ if (!f)
+ return;
+
if(f == lastfile)
- lastfile = 0;
+ lastfile = NULL;
Bterm(f->buf);
Bterm(f->transcript);
Strclose(&f->name);
(DIR) diff --git a/sam/mesg.c b/sam/mesg.c
@@ -465,7 +465,7 @@ inmesg(Tmesg type)
Write(1, c, i);
free(c);
} else
- dprint("snarf buffer too int64_t\n");
+ dprint("snarf buffer too long\n");
break;
case Tsetsnarf:
@@ -491,6 +491,7 @@ inmesg(Tmesg type)
break;
case Texit:
+ shutdown();
exit(EXIT_SUCCESS);
}
return true;
(DIR) diff --git a/sam/multi.c b/sam/multi.c
@@ -95,7 +95,7 @@ lookfile(String *s, bool fuzzy)
if (fuzzy){
char *ac = Strtoc(&file.filepptr[i]->name);
if (strcmp(basename(sc), ac) == 0)
- return free(ac), file.filepptr[i];
+ return free(sc), free(ac), file.filepptr[i];
if (!b && strstr(ac, sc))
b = file.filepptr[i];
@@ -103,5 +103,6 @@ lookfile(String *s, bool fuzzy)
}
}
+ free(sc);
return b;
}
(DIR) diff --git a/sam/sam.c b/sam/sam.c
@@ -106,8 +106,9 @@ main(int argc, char *argv[])
Strinit0(&genstr);
Strinit0(&rhs);
Strinit0(&wd);
- tempfile.listptr = emalloc(0);
Strinit0(&plan9cmd);
+
+ tempfile.listptr = emalloc(0);
home = getenv("HOME") ? getenv("HOME") : "/";
shpath = getenv("SHELL") ? getenv("SHELL") : shpath;
sh = basename(shpath);
@@ -133,16 +134,50 @@ main(int argc, char *argv[])
modnum++;
if(file.nused)
current(file.filepptr[0]);
+
setjmp(mainloop);
cmdloop();
+
trytoquit(); /* if we already q'ed, quitok will be true */
+
+ shutdown();
exit(EXIT_SUCCESS);
}
void
+shutdown(void)
+{
+ freecmd();
+ for (int i = 0; i < file.nused; i++)
+ Fclose(file.filepptr[i]);
+
+ if (!downloaded)
+ Fclose(cmd);
+
+ if (genc)
+ free(genc);
+
+ Strclose(&cmdstr);
+ Strclose(&lastpat);
+ Strclose(&lastregexp);
+ Strclose(&genstr);
+ Strclose(&rhs);
+ Strclose(&wd);
+ Strclose(&plan9cmd);
+
+ if (file.listptr)
+ free(file.listptr);
+
+ if (tempfile.listptr)
+ free(tempfile.listptr);
+
+ freecmdlists();
+}
+
+void
usage(void)
{
- dprint("usage: sam [-r machine] [-d] [-f] [-e] [-t samterm] [-s samname] FILE...\n");
+ fprintf(stderr, "usage: sam [-r machine] [-d] [-f] [-e] [-t samterm] [-s samname] FILE...\n");
exit(EXIT_FAILURE);
}
@@ -270,17 +305,16 @@ trytoquit(void)
int c;
File *f;
- if(!quitok)
-{
- for(c = 0; c<file.nused; c++){
+ if (!quitok){
+ for(c = 0; c < file.nused; c++){
f = file.filepptr[c];
- if(f!=cmd && f->state==Dirty){
+ if(f != cmd && f->state == Dirty){
quitok = true;
eof = false;
error(Echanges);
}
}
-}
+ }
}
void
@@ -720,7 +754,7 @@ settempfile(void)
{
if(tempfile.nalloc < file.nused){
free(tempfile.listptr);
- tempfile.listptr = emalloc(sizeof(*tempfile.filepptr)*file.nused);
+ tempfile.listptr = emalloc(sizeof(*tempfile.filepptr) * file.nused);
tempfile.nalloc = file.nused;
}
tempfile.nused = file.nused;
(DIR) diff --git a/sam/sam.h b/sam/sam.h
@@ -207,6 +207,8 @@ void error_s(Err, char*);
int execute(File*, Posn, Posn);
int filematch(File*, String*);
void filename(File*);
+void freecmd(void);
+void freecmdlists(void);
File *getfile(String*);
int getname(File*, String*, bool);
int64_t getnum(void);
@@ -237,7 +239,8 @@ void resetxec(void);
void rgrow(List*, Posn, Posn);
void samerr(char*);
void settempfile(void);
-int skipbl(void);
+void shutdown(void);
+int skipbl(void);
void snarf(File*, Posn, Posn, Buffer*, bool);
void sortname(File*);
void startup(char*, int, char**, char**);
(DIR) diff --git a/sam/unix.c b/sam/unix.c
@@ -125,14 +125,9 @@ waitfor(int pid)
void*
emalloc(uint64_t n)
{
- void *p;
-
- if (n < sizeof(int))
- n = sizeof(int);
- p = malloc(n);
- if(p == 0)
- panic("malloc fails");
- memset(p, 0, n);
+ void *p = calloc(1, n < sizeof(int)? sizeof(int) : n);
+ if (!p)
+ panic("malloc failed");
return p;
}
@@ -140,7 +135,7 @@ void*
erealloc(void *p, uint64_t n)
{
p = realloc(p, n);
- if(p == 0)
+ if(!p)
panic("realloc fails");
return p;
}