In commit 03607ace807b (configfs: implement binary attributes) we have serious trouble: +* Binary attributes, which are somewhat similar to sysfs binary attributes, +but with a few slight changes to semantics. The PAGE_SIZE limitation does not +apply, but the whole binary item must fit in single kernel vmalloc'ed buffer. +The write(2) calls from user space are buffered, and the attributes' +write_bin_attribute method will be invoked on the final close, therefore it is +imperative for user-space to check the return code of close(2) in order to +verify that the operation finished successfully. This is completely broken. ->release() is too late to return any errors - they won't reach the caller of close(2). ->flush() _is_ called early enough to pass return value to userland, but it's called every time descriptor is removed from descriptor table. IOW, if userland e.g. python code from hell has written some data to the attribute in question, then called a function that has ended up calling something in some misbegotten library that spawned a child, had it run and waited for it to exit, your ->flush() will be called twice. Which is fine for something like NFS sending the dirty data to server and checking that there's nothing left, but not for this kind of "gather data, then commit the entire thing at once" kind of interfaces. AFAICS, there's only one user in the tree right now (acpi/table/*/aml); no idea what drives the userland side. We might be able to paper over that mess by doing what /dev/st does - checking that file_count(file) == 1 in ->flush() instance and doing commit there in such case. It's not entirely reliable, though, and it's definitely not something I'd like to see spreading. Folks, please don't do that kind of userland ABIs; that kind of implicit commit on the final close is OK only if there's no error to report (e.g. if all checks can be done at write() time). Otherwise it's an invitation for trouble. And *ANYTHING* that tries to return an error from ->release() is very suspicious, no matter what. Again, in ->release() it's too late to return an error.