apps/examples/userfs: Fixes a bug with double freeing open data when dup'ed files are closed.
This commit is contained in:
parent
9ce13f74e7
commit
3dd64af3db
@ -83,6 +83,7 @@ struct ufstest_file_s
|
||||
struct ufstest_openfile_s
|
||||
{
|
||||
int16_t pos;
|
||||
int16_t crefs;
|
||||
FAR struct ufstest_file_s *file;
|
||||
};
|
||||
|
||||
@ -110,7 +111,7 @@ static int ufstest_ioctl(FAR void *volinfo, FAR void *openinfo, int cmd,
|
||||
unsigned long arg);
|
||||
static int ufstest_sync(FAR void *volinfo, FAR void *openinfo);
|
||||
static int ufstest_dup(FAR void *volinfo, FAR void *oldinfo,
|
||||
FAR void *newinfo);
|
||||
FAR void **newinfo);
|
||||
static int ufstest_fstat(FAR void *volinfo, FAR void *openinfo,
|
||||
FAR struct stat *buf);
|
||||
static int ufstest_opendir(FAR void *volinfo, FAR const char *relpath,
|
||||
@ -243,6 +244,14 @@ static int ufstest_open(FAR void *volinfo, FAR const char *relpath,
|
||||
|
||||
opriv->file = file;
|
||||
|
||||
/* Initiallly, there is one refernce count on the open data. This may
|
||||
* be incremented in the event that the file is dup'ed.
|
||||
*/
|
||||
|
||||
opriv->crefs = 1;
|
||||
|
||||
/* Return the opaque reference to the open data */
|
||||
|
||||
*openinfo = opriv;
|
||||
return OK;
|
||||
}
|
||||
@ -252,9 +261,19 @@ static int ufstest_open(FAR void *volinfo, FAR const char *relpath,
|
||||
|
||||
static int ufstest_close(FAR void *volinfo, FAR void *openinfo)
|
||||
{
|
||||
if (openinfo != NULL)
|
||||
FAR struct ufstest_openfile_s *opriv =
|
||||
(FAR struct ufstest_openfile_s *)openinfo;
|
||||
|
||||
if (opriv != NULL)
|
||||
{
|
||||
free(openinfo);
|
||||
if (opriv->crefs <= 1)
|
||||
{
|
||||
free(opriv);
|
||||
}
|
||||
else
|
||||
{
|
||||
opriv->crefs--;
|
||||
}
|
||||
}
|
||||
|
||||
return OK;
|
||||
@ -360,9 +379,18 @@ static int ufstest_sync(FAR void *volinfo, FAR void *openinfo)
|
||||
}
|
||||
|
||||
static int ufstest_dup(FAR void *volinfo, FAR void *oldinfo,
|
||||
FAR void *newinfo)
|
||||
FAR void **newinfo)
|
||||
{
|
||||
memcpy(newinfo, oldinfo, sizeof(struct ufstest_openfile_s));
|
||||
FAR struct ufstest_openfile_s *opriv =
|
||||
(FAR struct ufstest_openfile_s *)oldinfo;
|
||||
|
||||
/* Increment the reference count on the open info */
|
||||
|
||||
opriv->crefs++;
|
||||
|
||||
/* And just copy the openinfo reference */
|
||||
|
||||
*newinfo = oldinfo;
|
||||
return OK;
|
||||
}
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user