3#include <cuda/__cmath/ceil_div.h>
4#include <cuda_runtime.h>
17template <
typename Config>
23template <
typename Config>
35template <
typename Config>
38 std::vector<uint64_t> words(dense_packed_word_count<Config>(num_symbols), 0);
40 for (uint64_t symbol_index = 0; symbol_index < num_symbols; ++symbol_index) {
41 const uint8_t symbol =
43 const uint64_t word_index = symbol_index / symbols_per_word;
44 const auto bit_offset =
46 words[word_index] |= (
static_cast<uint64_t
>(symbol &
Config::symbolMask) << bit_offset);
57template <
typename Config>
59 const char* d_sequence,
62 cudaStream_t stream = {}
64 if (num_symbols == 0) {
67 constexpr uint64_t block_size = 256;
68 const uint64_t num_words = dense_packed_word_count<Config>(num_symbols);
69 const uint64_t grid_size = cuda::ceil_div(num_words, block_size);
71 <<<grid_size, block_size, 0, stream>>>(d_sequence, num_symbols, d_words);
#define CUSBF_CUDA_CALL(err)
Checks a CUDA runtime call and throws std::runtime_error on failure.
consteval bool separatorPositionAlwaysEncodesInvalid(char *input, uint64_t separatorPosition, uint64_t index)
Recursively tests whether placing the separator byte at any position in an input of valid bytes alway...
std::vector< uint64_t > pack_dense_sequence(std::string_view sequence)
Packs an ASCII sequence into dense symbolBits-wide uint64_t words.
void pack_dense_sequence_device(const char *d_sequence, uint64_t num_symbols, uint64_t *d_words, cudaStream_t stream={})
Packs a device-resident encoded byte sequence into dense uint64_t words.
constexpr uint64_t dense_packed_kmer_count(uint64_t num_symbols)
Returns the number of k-mer windows in a dense packed symbol sequence.
constexpr uint64_t dense_packed_word_count(uint64_t num_symbols)
Returns the number of uint64_t words required for num_symbols encoded symbols.
static constexpr uint64_t symbolWidth
Input bytes per symbol.
static constexpr uint64_t symbolMask
Low symbolBits mask for one encoded symbol.
static constexpr uint64_t symbolBits
Bits per packed symbol in a uint64_t k-mer.