| 408 | } |
| 409 | |
| 410 | static void make_block(const Bytes &goal, int depth, bool prev, |
| 411 | const std::deque<Instruction> &already_eaten, BlockList &list) |
| 412 | { |
| 413 | std::string logname = prev ? "MBP" : "MBN"; |
| 414 | //std::cerr << logname << ":" << depth << " " << goal << std::endl; |
| 415 | if (depth >= 3) { |
| 416 | return; |
| 417 | } |
| 418 | if (goal.size() == 0) { |
| 419 | //std::cerr << logname << " OK" << std::endl; |
| 420 | if (already_eaten.size() > 0) { |
| 421 | list.push_back(already_eaten); |
| 422 | } |
| 423 | return; |
| 424 | } |
| 425 | |
| 426 | bool simple_search = true; |
| 427 | |
| 428 | for (auto const& [key, seq] : sequences) { |
| 429 | /* For depth == 0, goal is part of an instruction */ |
| 430 | if (((depth > 0) && !simple_search) || (prev ? is_bytes_suffix(goal, key) : is_bytes_prefix(goal, key))) { |
| 431 | Bytes new_goal; |
| 432 | if (depth == 0) { |
| 433 | new_goal = (prev ? |
| 434 | Bytes(key.begin(), key.end() - goal.size()): |
| 435 | Bytes(key.begin() + goal.size(), key.end())); |
| 436 | } else { |
| 437 | new_goal = goal; |
| 438 | new_goal.insert(prev ? new_goal.begin() : new_goal.end(), key.begin(), key.end()); |
| 439 | } |
| 440 | |
| 441 | size_t eaten_size; |
| 442 | auto eaten = already_eaten; |
| 443 | Bytes eaten_goal = eat_instructions(new_goal, prev, eaten, &eaten_size); |
| 444 | //std::cerr << "*" << logname << ":" << depth << " " << goal << " -> " << new_goal << " -> " << eaten_goal << std::endl; |
| 445 | if (eaten_goal.size() < 4) { /* Else, we have not eaten enough to continue... */ |
| 446 | make_block(eaten_goal, depth+1, prev, eaten, list); |
| 447 | } |
| 448 | } |
| 449 | } |
| 450 | } |
| 451 | |
| 452 | static bool block_prefix(const Bytes &goal) |
| 453 | { |
no test coverage detected