diff options
Diffstat (limited to 'internal/syscallcompat')
| -rw-r--r-- | internal/syscallcompat/sys_common.go | 23 | 
1 files changed, 23 insertions, 0 deletions
diff --git a/internal/syscallcompat/sys_common.go b/internal/syscallcompat/sys_common.go index 4ce0208..a1aa66d 100644 --- a/internal/syscallcompat/sys_common.go +++ b/internal/syscallcompat/sys_common.go @@ -84,6 +84,29 @@ func Fgetxattr(fd int, attr string) (val []byte, err error) {  	return val, nil  } +// Lgetxattr is a wrapper around unix.Lgetxattr that handles the buffer sizing. +func Lgetxattr(path string, attr string) (val []byte, err error) { +	// See the buffer sizing comments in Fgetxattr. +	// TODO: smarter buffer sizing? +	buf := make([]byte, XATTR_BUFSZ) +	sz, err := unix.Lgetxattr(path, attr, buf) +	if err == syscall.ERANGE { +		// Do NOT return ERANGE - the user might retry ad inifinitum! +		return nil, syscall.EOVERFLOW +	} +	if err != nil { +		return nil, err +	} +	if sz >= XATTR_SIZE_MAX { +		return nil, syscall.EOVERFLOW +	} +	// Copy only the actually used bytes to a new (smaller) buffer +	// so "buf" never leaves the function and can be allocated on the stack. +	val = make([]byte, sz) +	copy(val, buf) +	return val, nil +} +  // Flistxattr is a wrapper for unix.Flistxattr that handles buffer sizing and  // parsing the returned blob to a string slice.  func Flistxattr(fd int) (attrs []string, err error) {  | 
