1
0
mirror of https://github.com/Zygo/bees.git synced 2025-05-17 21:35:45 +02:00

101 Commits

Author SHA1 Message Date
Zygo Blaxell
b7f9ce3f08 task: serialize Task execution when Tasks block due to mutex contention
Quite often we want to execute task B after task A finishes executing,
especially if tasks A and B attempt to acquire locks on the same objects.

Implement that capability in Task directly:  each Task holds a queue
of Tasks which will be executed strictly after this Task has finished
executing, or if the Task is destroyed.

Add a local queue to each TaskConsumer.  This queue contains a list
of Tasks which are to be executed by a single thread in sequential
order.  These tasks are executed before fetching any tasks from
TaskMaster.

Each time a Task finishes executing, the list of tasks appended to the
recently executed Task are spliced at the beginning of the thread's
TaskConsumer local queue.  These tasks will be executed in the same
thread in the same order they were appended to the recently executed Task.

If a Task is destroyed with a post-execution queue, that queue is
also inserted at the front of the current TaskConsumer's local queue.

If a Task is destroyed or somehow executed outside of a TaskConsumer
thread, or a TaskConsumer thread is destroyed, the local queue of Tasks
is wrapped in a "rescue_task" Task, and spliced before the head of the
global queue.  This preserves the sequential ordering of tasks.

In all cases the order of sequential execution of Tasks that are
appended to another Task is preserved.

The unused queue insertion functions are removed.

Exclusion is now simply a mutex, a bool, and a Task with an empty
function.  Tasks that queue up waiting for the mutex are stored in
Exclusion's Task, and Exclusion simply runs that task when the
ExclusionState is released.

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2021-06-11 20:49:15 -04:00
Zygo Blaxell
06a46e2736 chatter: add option to remove log level prefix
Some projects use only one log level, so there is no need to repeat it
for every line.

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2021-06-11 20:49:15 -04:00
Zygo Blaxell
e4c95d618a crucible: use '#include "crucible/...' everywhere
Make the #include syntax more consistent (even if it has no effect).

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2021-06-11 20:49:15 -04:00
Zygo Blaxell
032c740678 process: SIGCLD is not portable
MUSL libc doesn't have it, for instance.

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2021-06-11 20:49:15 -04:00
Zygo Blaxell
f8a8704135 ntoa: fix bits_ntoa formatting and error handling
Get rid of an assert in bits_ntoa.  Throw an exception instead.

Fix hex formatting (adding "0x" before a decimal number is not
the correct way to format hex strings).

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2021-04-23 08:20:03 -04:00
Zygo Blaxell
bcf3e7de3e uuid: drop dependency on uuid.h
The weird things distros do to the path where uuid.h gets installed
have broken bees builds for the last time.

We were only using uuid to support a legacy feature that was removed
over four years ago.

Hypothetical users who are upgrading directly from bees v0.1 should
probably restart all the crawlers anyway--there were bugs.  Also, if any
such users exist, I respect their tremendous patience with the horrible
performance all these years--bees got about 30x faster since v0.1.

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2021-04-23 08:16:50 -04:00
Zygo Blaxell
7f660f50b8 lib: fs: stop using libbtrfs-dev helper functions to re-enable buffer length checks
The Linux kernel's btrfs headers are better than the libbtrfs-dev headers:

	- the libbtrfs-dev headers have C++ language compatibility issues

	- upstream version in Linux kernel is more accurate and up to date

	- macros in libbtrfs-dev's ctree.h hide information that would
	enable bees to perform runtime buffer length checking

	- enum types whose presence cannot be detected with #ifdef

When accessing members of metadata items from the filesystem, we want
to verify that the member we are accessing is within the boundaries of
the item that was retrieved; otherwise, a memory access violation may
occur or garbage may be returned to the caller.  A simple C++ template,
given a pointer to a structure member and a buffer, can determine that
the buffer contains enough bytes to safely access a struct member.
This was implemented back in 2016, but left unused due to ctree.h issues.

Some btrfs metadata structures have variable length despite using a
fixed-size in-memory structure.  The members that appear earliest in
the structure contain information about which following members of the
structure are used.  The item stored in the filesystem is truncated after
the last used member, and all following members must not be accessed.

'btrfs_stack_*' accessor macros obscure the memory boundaries of the
members they access, which makes it impossible for a C++ template to
verify the memory access.  If the template checks the length of the
entire structure, it will find an access violation for variable-length
metadata items because the item is rarely large enough for the entire
structure.

Get rid of all the libbtrfs-dev accessor macros and reimplement them
with the necessary buffer length checks.

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2021-02-22 20:06:43 -05:00
Zygo Blaxell
6eb7afa65c build: include localconf everywhere
Overriding makeflags did not work from localconf in the src, lib, or
test directories.

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2021-02-22 20:06:43 -05:00
Zygo Blaxell
c0149d72b7 fs: use Spanner to refer to ioctl arg buffer instead of making vector copies
This avoids some allocations and copying.

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2020-12-17 18:07:36 -05:00
Zygo Blaxell
f45e379802 fs: deprecate vector<char>
Use uint8_t when we mean uint8_t, i.e. vector<uint8_t> instead of
vector<char>.

Add a template parameter instead of vector so we can swap in a
non-copying data type.

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2020-12-17 18:07:36 -05:00
Zygo Blaxell
180bb60cde fs: add support and workarounds for btrfs fs_info v2
Define a local copy of the header that has fields for the csum type
and length, so we can build in places that haven't caught up to kernel
5.5 headers yet.

The reason why the csum type and length are not unconditionally filled
in eludes me.  csum_length is necessarily non-zero, and the cost of
the conditional is worse than the cost of the copy, so the whole flags
dance is a WTF...but it's part of the kernel API now, so it's too late
to NAK it.

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2020-12-17 18:07:36 -05:00
Zygo Blaxell
c80af1cb4f fd: deprecate Resource in favor of NamedPtr
Rewrite Fd using a much simpler named resource template class with
a more straightforward derivation strategy.

Behavior change:  we no longer throw an exception while calling get_fd()
on a closed Fd.  This does not seem to bother any current callers except
for the tests.

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2020-12-17 18:06:44 -05:00
Zygo Blaxell
8a2fb75462 fd: move relative path string to library
Use a single static variable located in the library, instead of
having a separate one for each compilation unit.

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2020-12-17 17:54:52 -05:00
Zygo Blaxell
0c84302d9a lib: don't rebuild libcrucible unless there is a version change
If we create an identical .version.cc then don't bother keeping it.
This prevents libcrucible from rebuilding if there are no other changes,
which in turn prevents all the binaries from rebuilding unconditionally.

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2020-12-17 17:54:51 -05:00
Zygo Blaxell
1086900a9d string: second argument to stoull is technically a nullptr
This comes up if too many compiler warnings are enabled.

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2020-12-17 17:54:51 -05:00
Zygo Blaxell
97c167d63a fs: don't zero-fill btrfs data containers
The kernel does it already, and we gain a little performance here because
we do it so often.

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2020-12-17 17:54:51 -05:00
Zygo Blaxell
459071597b fs: make operator<() for search ioctl inline
Perf blames this operator for >1% of instructions with -O2, and
70% of instructions without -O2.

Let the compiler inline the function.

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2020-12-17 17:54:51 -05:00
Zygo Blaxell
187d12fc25 fs: always use container's actual size not requested size
The requested size may not match the final size of the container,
so consistently use the container's size after prepare(), not the
requested size.

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2020-12-17 17:54:51 -05:00
Zygo Blaxell
62a20ebf9c chatter: make it build with clang
Silence the unused variable warning.  The compiler is correct, but we
may implement line-level debug at some point in the future, so we
want to keep the member and parameters.

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2020-12-17 17:54:51 -05:00
Zygo Blaxell
b7b18d9fa1 extentwalker: make it build with clang
Remove unused MAX_OFFSET.

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2020-12-17 17:54:51 -05:00
Zygo Blaxell
e34237886d process: make it build with clang
Get rid of unused template instantiation.

Drop the unused realtime signals from the ntoa table.  If in the future
we really need to solve clang's issue with them, we'll address it then.

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2020-12-17 17:54:51 -05:00
Zygo Blaxell
15ab981d9e bees: replace uncaught_exception(), deprecated in C++17
uncaught_exception() had only the one valid use case, and it can be
reimplemented by literally calling current_exception() instead.

current_exception() has several valid use cases, so it is not likely
to be deprecated any time soon.

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2020-10-09 12:07:10 -04:00
Andrey Brusnik
9514b89405 fs: Change array syntax to pointer syntax
Fixes #141
Signed-off-by: Andrey Brusnik <pixeliz3d@protonmail.com>
2020-04-09 22:09:20 +03:00
Zygo Blaxell
4363463342 process: Fix gettid() ambiguity with glibc >= 2.30
In version 2.30 glibc added it's own gettid() function. This resulted in
"error: call of overloaded ‘gettid()’ is ambiguous" because gettid()
now exists in both namespace crucible and std.

For now, use explicit references to namespace crucible.  This continues
to work with new and old libc without having to test specific library
versions.

At some point, glibc gettid() will be deployed widely enough that we can
remove the crucible version entirely.

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2019-10-30 00:12:33 -04:00
Zygo Blaxell
b3a8fcb553 lib: add cityhash function
CityHash64 appears to be the fastest available block hashing algorithm
that is good enough for dedupe.  It takes much less CPU than the CRC64
function, and avoids hash-collision problems with file formats that use
CRC64 as an integrity check on 4K block boundaries.

Extracted from git://github.com/google/cityhash with the "CRC" hash
functions (which require Intel/AMD CPU support) removed.  We don't
need those, and they introduce a new (if only theoretical) build-time
dependency.

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2019-06-12 22:48:06 -04:00
Zygo Blaxell
228747a8f8 lib: fix non-local lambda expression cannot have a capture-default
We got away with this because GCC 4.8 (and apparently every GCC prior
to 9) didn't notice or care, and because there is nothing referenced
inside the lambda function body that isn't accessible from any other
kind of function body (i.e. the capture wasn't needed at all).

GCC 9 now enforces what the C++ standard said all along:  there is
no need to allow capture-default in this case, so it is not.

Fix by removing the offending capture-default.

Fixes: https://github.com/Zygo/bees/issues/112
Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2019-06-12 22:48:06 -04:00
Zygo Blaxell
87e8a21c41 fs: do not emulate extent-same by clone
It is not possible to emulate extent-same by clone in a safe way.
EXTENT_SAME has been supported in btrfs since kernel 3.13, which
is much too old to contemplate running bees on.

Remove this dangerous and unused function.

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2019-06-12 22:48:06 -04:00
Zygo Blaxell
e3747320cf BtrfsExtentWalker: use a buffer at least as large as a btrfs metadata page to avoid EOVERFLOW
We are getting a lot of exceptions when an inline extent is too large for the
TREE_SEARCH_V2 buffer.  This disrupts ExtentWalker's extent boundary
search when there is an inline extent at the beginning of a file:

	# fiemap foo
	Log 0x0..0x1000 Phy 0x0..0x1000 Flags FIEMAP_EXTENT_NOT_ALIGNED|FIEMAP_EXTENT_DATA_INLINE
	Log 0x1000..0x2000 Phy 0x7307f9000..0x7307fa000 Flags 0
	Log 0x2000..0x3000 Phy 0x731078000..0x731079000 Flags 0
	Log 0x3000..0x5000 Phy 0x73127d000..0x73127f000 Flags FIEMAP_EXTENT_ENCODED
	Log 0x5000..0x6000 Phy 0x73137a000..0x73137b000 Flags 0
	Log 0x6000..0x7000 Phy 0x731683000..0x731684000 Flags 0
	Log 0x7000..0x8000 Phy 0x73224f000..0x732250000 Flags 0
	Log 0x8000..0x9000 Phy 0x7323c9000..0x7323ca000 Flags 0
	Log 0x9000..0xb000 Phy 0x732425000..0x732427000 Flags FIEMAP_EXTENT_ENCODED
	Log 0xb000..0xc000 Phy 0x732598000..0x732599000 Flags 0
	Log 0xc000..0xd000 Phy 0x7325d5000..0x7325d6000 Flags FIEMAP_EXTENT_LAST

	# fiewalk foo
	exception type std::system_error: BTRFS_IOC_TREE_SEARCH_V2: /tmp/foo at fs.cc:844: Value too large for defined data type

Normally crawlers simply skip over inline extents, but ExtentWalker will
seek backward from the first non-inline extent to confirm that it has
an accurate starting block for the target extent.  This fails when it
encounters the first inline extent.

strace reveals that buffer size is too small for the first extent,
as seen here:

	ioctl(3, BTRFS_IOC_TREE_SEARCH_V2, {key={tree_id=258, min_objectid=78897856, max_objectid=UINT64_MAX, min_offset=0, max_offset=UINT64_MAX, min_transid=0, max_transid=UINT64_MAX, min_type=BTRFS_EXTENT_DATA_KEY, max_type=BTRFS_EXTENT_DATA_KEY, nr_items=16}, buf_size=1360} => {buf_size=1418}) = -1 EOVERFLOW (Value too large for defined data type)

Fix this by increasing the buffer size until it can handle the largest
possible object on the largest possible btrfs metadata page (65536 bytes).
BtrfsExtentWalker already has optimizations to minimize the allocation
cost, so we don't need any changes there.

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2019-06-12 22:48:05 -04:00
Zygo Blaxell
978c577412 status: report number of active worker threads in status output
This is especially useful when dynamic load management allocates more
worker threads than active tasks, so the extra threads are effectively
invisible.

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2019-01-07 22:52:12 -05:00
Zygo Blaxell
4021dd42ca task: queue and run exactly once per instance
Enable much simpler Task management:  each time a Task needs to be done
at least once in the future, simply invoke the run() method on the Task.
The Task will ensure that it only runs once, only appears in a queue
once, and will run again if a run request is made while the Task is
already running.

Make the queue policy a member of the Task rather than a method.  This
enables Tasks to reschedule themselves, possibly on the appropriate queue
if we have more than one of those some day.

This happens to make Tasks more similar to Linux kernel workers.
This similarity is coincidental, but not undesirable.

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2019-01-07 22:48:15 -05:00
Zygo Blaxell
4a1971bce5 process: SIGUNUSED is deprecated
SIGUNUSED is not defined in many environments (it seems to be defined
in only one I've tried so far).  Hide the reference with #ifdef.

Fixes: https://github.com/Zygo/bees/issues/94
Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2018-12-13 18:03:35 -05:00
Zygo Blaxell
7933ccb660 build: make libcrucible a static library
libcrucible at one time in the distant past had to be a shared library
to force global C++ object initialization; however, this is no longer
required.

Make libcrucible static to solve various rpath and soname versioning
issues, especially when distros try (unwisely) to package the library
separately.

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2018-12-09 23:39:44 -05:00
Zygo Blaxell
cbc6725f0f time: separate sleep time calculation from sleep_for method
We need to replace nanosleeps with condition variables so that we
can implement BeesContext::stop.  Export the time calculation from
sleep_for() into a new method called sleep_time().

If the thread executing RateLimiter::sleep_for() is interrupted, it will
no longer be able to restart, as the sleep_time() method is destructive.
This calls for further refactoring of sleep_time() into destructive
and non-destructive parts; however, there are currently no users of
sleep_for() which rely on being able to restart after being interrupted
by a signal.

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2018-12-09 23:45:52 -05:00
Zygo Blaxell
0e42c75f5a process: ntoa function for signals
This enables signal numbers to be translated to names.

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2018-12-09 23:45:52 -05:00
Zygo Blaxell
4e962172a7 task: add cancel method
Add a method to have TaskMaster discard any entries in its queue, terminate
all worker threads, and prevent any new Tasks from being queued.

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2018-12-09 01:15:24 -05:00
Kai Krakow
6c68e81da7
Makefile: Fix git usage for non-git source archive
We didn't take enough care to fix all invocations of git in this
scenario.

Fixes: 32d2739 ("Makefile: Specify version when building from tarball")
Signed-off-by: Kai Krakow <kai@kaishome.de>
2018-11-18 16:10:32 +01:00
Zygo Blaxell
0d5c018c3c fs: if search fails, return empty result set
Make sure the result set is empty before running the ioctl in case
something tries to consume the result without checking the error status.

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2018-11-16 17:20:49 -05:00
Zygo Blaxell
a676928ed5 fs: remove thread_local storage
If we are not zero-filling containers then the overhead of allocating them
on each use is negligible.  The effect that the thread_local containers
were having on RAM usage was very non-negligible.

Use dynamic containers (members or stack objects) for better control
of object lifetimes and much lower peak RAM usage.  They're a tiny bit
faster, too.

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2018-11-08 23:55:13 -05:00
Kai Krakow
c69a954d8f
Makefile: Bring back -O3 in a downstream-compatible way
This commit brings back -O3 but in an overridable way. This should make
downstream distributions happy enough to accept it.

While at the subject, let's apply the same fixup logic to LDFLAGS, too.

This commit also properly gets rid of the implicit rules which collided
too easily with the depends.mk.

Signed-off-by: Kai Krakow <kai@kaishome.de>
2018-11-08 03:23:40 +01:00
Kai Krakow
f2dec480a6
Makefile: mkdir .depends only when needed
Signed-off-by: Kai Krakow <kai@kaishome.de>
2018-11-08 02:56:48 +01:00
Zygo Blaxell
8cbd6fc67a fs: support LOGICAL_INO_V2
Automatically fall back to LOGICAL_INO if LOGICAL_INO_V2 fails and no
_V2 flags are used.

Add methods to set the flags argument with build portability to older
headers.

Use thread_local storage for the somewhat large buffers used by
LOGICAL_INO_V2 (and other users of BtrfsDataContainer like INO_PATHS).

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2018-11-05 21:12:36 -05:00
Zygo Blaxell
9dbe2d6fee bees: add -G/--thread-min option for minimum thread count
The -g option limits the number of worker threads when the target load
average is exceeded.  On some systems the load normally runs high, and
continuous bees operation is required to avoid running out of disk space.

Add a -G/--thread-min option to force at least some threads to continue
running.

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2018-09-14 23:50:07 -04:00
Zygo Blaxell
e66086516f bees: dynamic thread pool size based on system load average
Add -g / --loadavg-target parameter to track system load and add or
remove bees worker threads dynamically to keep system load close to the
loadavg target.  Thread count may vary from zero to the maximum
specified by -c or -C, and is adjusted every 5 seconds.

This is better than implementing a similar load average scheme from
outside of the process (though that is still possible) because the
in-process load tracker does not disrupt the performance timing feedback
mechanisms as a freezer cgroup or SIGSTOP would when controlling bees
from outside.  The internal load average tracker can also adjust the
number of active threads while an external tracker can only choose from
the maximum or zero.

Also fix a bug where a Task could deadlock waiting for itself to exit
if it tries to insert a new Task after the number of worker threads has
been set to zero.

Also correct usage message for --scan-mode (values are 0..2) since
we are touching adjacent lines anyway.

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2018-09-14 23:50:03 -04:00
Kai Krakow
51108f839d Makefile: Due to VPATH, libcrucible links to hard-coded libuuid path
Due to VPATH and how make resolves source paths, libcrucible.so ends up
with a hard-coded path to link against libuuid.so. Let's fix it by
turning the general rule into an explicit rule for libcrucible.so.

Signed-off-by: Kai Krakow <kai@kaishome.de>
2018-09-08 03:07:20 +02:00
Kai Krakow
4417b18d9e Makefile: .version.o is made from a generated file
We should probably not put it into the objects list. Let's instead
explicitly put it as a depend of libcrucible.so.

This allows us to not use *.cc as a depend for .version.cc which makes
more sense as CRUCIBLE_OBJS is also explicitly defined and not built
from wildcards.

Signed-off-by: Kai Krakow <kai@kaishome.de>
2018-09-08 02:59:54 +02:00
Kai Krakow
8636312cab Compilation: Let the code know about package config
This commit adds support for putting package configuration options into
header files. This is needed to prepare reading config files from /etc.

Signed-off-by: Kai Krakow <kai@kaishome.de>
2018-09-08 02:59:54 +02:00
Zygo Blaxell
e9aef89293 fs: fix FTBFS on GCC 8
The memset is just doing an assignment from one dereferenced pointer to
another, so do an assignment to keep GCC 8 happy.

Fixes: https://github.com/Zygo/bees/issues/64

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2018-05-18 00:15:37 -04:00
Zygo Blaxell
90c32c3f05 crucible: MAP_32BIT is not defined on ARM
Also fix a stray #if that should be #ifdef.

Closes:  https://github.com/Zygo/bees/issues/59

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2018-02-25 10:08:44 -05:00
Zygo Blaxell
5c1b45d67c extentwalker: remove wrong constraint check
Extents that extend past EOF will have ipos = (file size rounded up
to next block) and e.end() = (file size not rounded), which fails this
constraint check.

The constraint check is wrong.  Remove it for now.

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2018-02-07 00:07:57 -05:00
Zygo Blaxell
2aacdcd95f time: add update_monotonic to RateEstimator
update_monotonic does not reset the counter if a new count is smaller than
earlier counts.  Useful when consuming an unsorted stream of eveent counts.

Signed-off-by: Zygo Blaxell <bees@furryterror.org>
2018-01-29 00:51:13 -05:00