Retrieves a WildcardMatchConfig that would restore this module's runtime configuration.
| 405 | // Retrieves a WildcardMatchConfig that would restore this module's |
| 406 | // runtime configuration. |
| 407 | CommandResponse WildcardMatch::GetRuntimeConfig(const bess::pb::EmptyArg &) { |
| 408 | bess::pb::WildcardMatchConfig resp; |
| 409 | using rule_t = bess::pb::WildcardMatchCommandAddArg; |
| 410 | |
| 411 | resp.set_default_gate(default_gate_); |
| 412 | |
| 413 | // Each tuple provides a single mask, which may have many data-matches. |
| 414 | for (auto &tuple : tuples_) { |
| 415 | wm_hkey_t mask = tuple.mask; |
| 416 | // Each entry in the hash table has priority, ogate, and the data |
| 417 | // (one datum per field, under the mask for this field). |
| 418 | for (auto &entry : tuple.ht) { |
| 419 | // Create the rule instance |
| 420 | rule_t *rule = resp.add_rules(); |
| 421 | rule->set_priority(entry.second.priority); |
| 422 | rule->set_gate(entry.second.ogate); |
| 423 | |
| 424 | uint8_t *entry_data = reinterpret_cast<uint8_t *>(entry.first.u64_arr); |
| 425 | uint8_t *entry_mask = reinterpret_cast<uint8_t *>(mask.u64_arr); |
| 426 | // Then fill in each field |
| 427 | for (auto &field : fields_) { |
| 428 | bess::pb::FieldData *valuedata = rule->add_values(); |
| 429 | valuedata->set_value_bin(entry_data + field.pos, field.size); |
| 430 | bess::pb::FieldData *maskdata = rule->add_masks(); |
| 431 | maskdata->set_value_bin(entry_mask + field.pos, field.size); |
| 432 | } |
| 433 | } |
| 434 | } |
| 435 | // Sort the results so that they're always predictable. |
| 436 | std::sort(resp.mutable_rules()->begin(), resp.mutable_rules()->end(), |
| 437 | [this](const rule_t &a, const rule_t &b) { |
| 438 | // Sort is by priority, then gate, then masks, then values. |
| 439 | // The precise order is not as important as consistency. |
| 440 | if (a.priority() != b.priority()) { |
| 441 | return a.priority() < b.priority(); |
| 442 | } |
| 443 | if (a.gate() != b.gate()) { |
| 444 | return a.gate() < b.gate(); |
| 445 | } |
| 446 | for (size_t i = 0; i < fields_.size(); i++) { |
| 447 | if (a.masks(i).value_bin() != b.masks(i).value_bin()) { |
| 448 | return a.masks(i).value_bin() < b.masks(i).value_bin(); |
| 449 | } |
| 450 | } |
| 451 | for (size_t i = 0; i < fields_.size(); i++) { |
| 452 | if (a.values(i).value_bin() != b.values(i).value_bin()) { |
| 453 | return a.values(i).value_bin() < b.values(i).value_bin(); |
| 454 | } |
| 455 | } |
| 456 | return false; |
| 457 | }); |
| 458 | return CommandSuccess(resp); |
| 459 | } |
| 460 | |
| 461 | CommandResponse WildcardMatch::CommandSetDefaultGate( |
| 462 | const bess::pb::WildcardMatchCommandSetDefaultGateArg &arg) { |