| 510 | if (s[0] == '\0' || *end != '\0' || v == 0) { |
| 511 | fprintf(stderr, "ds4-agent: invalid value for %s: %s\n", opt, s); |
| 512 | exit(2); |
| 513 | } |
| 514 | return (uint64_t)v; |
| 515 | } |
| 516 | |
| 517 | static float parse_float_range(const char *s, const char *opt, float min, float max) { |
| 518 | char *end = NULL; |
| 519 | float v = strtof(s, &end); |
| 520 | if (s[0] == '\0' || *end != '\0' || !isfinite(v) || v < min || v > max) { |
| 521 | fprintf(stderr, "ds4-agent: invalid value for %s: %s\n", opt, s); |
| 522 | exit(2); |
| 523 | } |
| 524 | return v; |
| 525 | } |
| 526 | |
| 527 | static ds4_backend parse_backend(const char *s) { |
| 528 | if (!strcmp(s, "metal")) return DS4_BACKEND_METAL; |
| 529 | if (!strcmp(s, "cuda")) return DS4_BACKEND_CUDA; |
| 530 | if (!strcmp(s, "cpu")) return DS4_BACKEND_CPU; |
| 531 | fprintf(stderr, "ds4-agent: invalid backend: %s\n", s); |
| 532 | exit(2); |
| 533 | } |
| 534 | |
| 535 | static ds4_backend default_backend(void) { |
| 536 | #ifdef DS4_NO_GPU |
| 537 | return DS4_BACKEND_CPU; |
| 538 | #elif defined(__APPLE__) |
| 539 | return DS4_BACKEND_METAL; |
| 540 | #else |
| 541 | return DS4_BACKEND_CUDA; |
| 542 | #endif |
| 543 | } |
| 544 | |
| 545 | static double now_sec(void) { |
| 546 | struct timespec ts; |
| 547 | clock_gettime(CLOCK_MONOTONIC, &ts); |
| 548 | return (double)ts.tv_sec + (double)ts.tv_nsec * 1.0e-9; |
| 549 | } |
| 550 | |
| 551 | static void usage(FILE *fp, const char *topic) { |
| 552 | ds4_help_print(fp, DS4_HELP_AGENT, topic); |
| 553 | } |
| 554 | |
| 555 | static const char *need_arg(int *i, int argc, char **argv, const char *opt) { |
| 556 | if (*i + 1 >= argc) { |
| 557 | fprintf(stderr, "ds4-agent: missing value for %s\n", opt); |
| 558 | exit(2); |
| 559 | } |
| 560 | return argv[++(*i)]; |
| 561 | } |
| 562 | |
| 563 | static agent_config parse_options(int argc, char **argv) { |
| 564 | agent_config c = { |
| 565 | .engine = { |
| 566 | .model_path = "ds4flash.gguf", |
| 567 | .backend = default_backend(), |
| 568 | .mtp_draft_tokens = 1, |
| 569 | .mtp_margin = 3.0f, |
no test coverage detected