Pārlūkot izejas kodu

Add get_source_cap command

It prints the most recently advertised PDOs in a reasonable format.  The
types it doesn't know about are printed as hex so that someone
knowledgeable can still get the information they need.  For now, it only
knows about fixed PDOs, so variable and battery PDOs will be shown as
hex.

Since this means we remember the most recent Source_Capabilities, it's
now becoming possible to send a new Request without sending a
Get_Source_Cap message first.  That's not actually done yet, but I'd
like to do it that way.  I'd also at some point like to make a
lower-current Request when the PD Buddy Sink's output is disabled, but
again, that's still to come.
Clara Hobbs 6 gadus atpakaļ
vecāks
revīzija
cea3f92e63
4 mainītis faili ar 110 papildinājumiem un 4 dzēšanām
  1. 10
    2
      src/device_policy_manager.c
  2. 3
    0
      src/device_policy_manager.h
  3. 4
    2
      src/policy_engine.c
  4. 93
    0
      src/shell.c

+ 10
- 2
src/device_policy_manager.c Parādīt failu

29
 
29
 
30
 
30
 
31
 bool pdb_dpm_output_enabled = true;
31
 bool pdb_dpm_output_enabled = true;
32
-
33
 bool pdb_dpm_led_pd_status = true;
32
 bool pdb_dpm_led_pd_status = true;
34
-
35
 bool pdb_dpm_usb_comms = false;
33
 bool pdb_dpm_usb_comms = false;
36
 
34
 
35
+const union pd_msg *pdb_dpm_capabilities = NULL;
36
+
37
 
37
 
38
 /* The current draw when the output is disabled */
38
 /* The current draw when the output is disabled */
39
 #define DPM_MIN_CURRENT PD_MA2PDI(100)
39
 #define DPM_MIN_CURRENT PD_MA2PDI(100)
49
 
49
 
50
 bool pdb_dpm_evaluate_capability(const union pd_msg *capabilities, union pd_msg *request)
50
 bool pdb_dpm_evaluate_capability(const union pd_msg *capabilities, union pd_msg *request)
51
 {
51
 {
52
+    /* Update the stored Source_Capabilities */
53
+    if (capabilities != NULL) {
54
+        if (pdb_dpm_capabilities != NULL) {
55
+            chPoolFree(&pdb_msg_pool, (union pd_msg *) pdb_dpm_capabilities);
56
+        }
57
+        pdb_dpm_capabilities = capabilities;
58
+    }
59
+
52
     /* Get the current configuration */
60
     /* Get the current configuration */
53
     struct pdb_config *cfg = pdb_config_flash_read();
61
     struct pdb_config *cfg = pdb_config_flash_read();
54
     /* Get the number of PDOs */
62
     /* Get the number of PDOs */

+ 3
- 0
src/device_policy_manager.h Parādīt failu

33
 /* Whether the device is capable of USB communications */
33
 /* Whether the device is capable of USB communications */
34
 extern bool pdb_dpm_usb_comms;
34
 extern bool pdb_dpm_usb_comms;
35
 
35
 
36
+/* The most recently received Source_Capabilities message */
37
+extern const union pd_msg *pdb_dpm_capabilities;
38
+
36
 
39
 
37
 /*
40
 /*
38
  * Create a Request message based on the given Source_Capabilities message.
41
  * Create a Request message based on the given Source_Capabilities message.

+ 4
- 2
src/policy_engine.c Parādīt failu

142
     /* Ask the DPM what to request */
142
     /* Ask the DPM what to request */
143
     capability_match = pdb_dpm_evaluate_capability(policy_engine_message,
143
     capability_match = pdb_dpm_evaluate_capability(policy_engine_message,
144
             last_dpm_request);
144
             last_dpm_request);
145
-    /* Free the Source_Capabilities message */
146
-    chPoolFree(&pdb_msg_pool, policy_engine_message);
145
+    /* It's up to the DPM to free the Source_Capabilities message, which it can
146
+     * do whenever it sees fit.  Just remove our reference to it since we won't
147
+     * know when it's no longer valid. */
148
+    policy_engine_message = NULL;
147
 
149
 
148
     return PESinkSelectCap;
150
     return PESinkSelectCap;
149
 }
151
 }

+ 93
- 0
src/shell.c Parādīt failu

52
     .status = PDB_CONFIG_STATUS_VALID
52
     .status = PDB_CONFIG_STATUS_VALID
53
 };
53
 };
54
 
54
 
55
+/*
56
+ * Helper functions for printing PDOs
57
+ */
58
+static void print_src_fixed_pdo(BaseSequentialStream *chp, uint32_t pdo)
59
+{
60
+    int tmp;
61
+
62
+    chprintf(chp, "\ttype: fixed\r\n");
63
+
64
+    /* Dual-role power */
65
+    tmp = (pdo & PD_PDO_SRC_FIXED_DUAL_ROLE_PWR) >> PD_PDO_SRC_FIXED_DUAL_ROLE_PWR_SHIFT;
66
+    if (tmp) {
67
+        chprintf(chp, "\tdual_role_pwr: %d\r\n", tmp);
68
+    }
69
+
70
+    /* USB Suspend Supported */
71
+    tmp = (pdo & PD_PDO_SRC_FIXED_USB_SUSPEND) >> PD_PDO_SRC_FIXED_USB_SUSPEND_SHIFT;
72
+    if (tmp) {
73
+        chprintf(chp, "\tusb_suspend: %d\r\n", tmp);
74
+    }
75
+
76
+    /* Unconstrained power */
77
+    tmp = (pdo & PD_PDO_SRC_FIXED_UNCONSTRAINED) >> PD_PDO_SRC_FIXED_UNCONSTRAINED_SHIFT;
78
+    if (tmp) {
79
+        chprintf(chp, "\tunconstrained_pwr: %d\r\n", tmp);
80
+    }
81
+
82
+    /* USB communications capable */
83
+    tmp = (pdo & PD_PDO_SRC_FIXED_USB_COMMS) >> PD_PDO_SRC_FIXED_USB_COMMS_SHIFT;
84
+    if (tmp) {
85
+        chprintf(chp, "\tusb_comms: %d\r\n", tmp);
86
+    }
87
+
88
+    /* Dual-role data */
89
+    tmp = (pdo & PD_PDO_SRC_FIXED_DUAL_ROLE_DATA) >> PD_PDO_SRC_FIXED_DUAL_ROLE_DATA_SHIFT;
90
+    if (tmp) {
91
+        chprintf(chp, "\tdual_role_data: %d\r\n", tmp);
92
+    }
93
+
94
+    /* Peak current */
95
+    tmp = (pdo & PD_PDO_SRC_FIXED_PEAK_CURRENT) >> PD_PDO_SRC_FIXED_PEAK_CURRENT_SHIFT;
96
+    if (tmp) {
97
+        chprintf(chp, "\tpeak_i: %d\r\n", tmp);
98
+    }
99
+
100
+    /* Voltage */
101
+    tmp = (pdo & PD_PDO_SRC_FIXED_VOLTAGE) >> PD_PDO_SRC_FIXED_VOLTAGE_SHIFT;
102
+    chprintf(chp, "\tv: %d.%02d V\r\n", PD_PDV_V(tmp), PD_PDV_CV(tmp));
103
+
104
+    /* Maximum current */
105
+    tmp = (pdo & PD_PDO_SRC_FIXED_CURRENT) >> PD_PDO_SRC_FIXED_CURRENT_SHIFT;
106
+    chprintf(chp, "\ti: %d.%02d A\r\n", PD_PDI_A(tmp), PD_PDI_CA(tmp));
107
+}
108
+
109
+static void print_src_pdo(BaseSequentialStream *chp, uint32_t pdo, uint8_t index)
110
+{
111
+    /* If we have a positive index, print a label for the PDO */
112
+    if (index) {
113
+        chprintf(chp, "PDO %d:\r\n", index);
114
+    }
115
+
116
+    /* Select the appropriate method for printing the PDO itself */
117
+    if ((pdo & PD_PDO_TYPE) == PD_PDO_TYPE_FIXED) {
118
+        print_src_fixed_pdo(chp, pdo);
119
+    } else {
120
+        /* Unknown PDO, just print it as hex */
121
+        chprintf(chp, "\t%08X\r\n", pdo);
122
+    }
123
+}
124
+
125
+
55
 /*
126
 /*
56
  * Command functions
127
  * Command functions
57
  */
128
  */
272
     }
343
     }
273
 }
344
 }
274
 
345
 
346
+static void cmd_get_source_cap(BaseSequentialStream *chp, int argc, char *argv[])
347
+{
348
+    (void) argv;
349
+    if (argc > 0) {
350
+        chprintf(chp, "Usage: get_source_cap\r\n");
351
+        return;
352
+    }
353
+
354
+    /* If we haven't seen any Source_Capabilities yet, bail out now */
355
+    if (pdb_dpm_capabilities == NULL) {
356
+        chprintf(chp, "No Source_Capabilities\r\n");
357
+        return;
358
+    }
359
+
360
+    /* Print all the PDOs */
361
+    uint8_t numobj = PD_NUMOBJ_GET(pdb_dpm_capabilities);
362
+    for (uint8_t i = 0; i < numobj; i++) {
363
+        print_src_pdo(chp, pdb_dpm_capabilities->obj[i], i+1);
364
+    }
365
+}
366
+
275
 /*
367
 /*
276
  * List of shell commands
368
  * List of shell commands
277
  */
369
  */
290
     /* TODO {"set_v_range", cmd_set_v_range, "Set the minimum and maximum voltage in millivolts"},*/
382
     /* TODO {"set_v_range", cmd_set_v_range, "Set the minimum and maximum voltage in millivolts"},*/
291
     {"identify", cmd_identify, "Blink the LED to identify the device"},
383
     {"identify", cmd_identify, "Blink the LED to identify the device"},
292
     {"output", cmd_output, "Get or set the output status"},
384
     {"output", cmd_output, "Get or set the output status"},
385
+    {"get_source_cap", cmd_get_source_cap, "Print the capabilities of the PD source"},
293
     {NULL, NULL, NULL}
386
     {NULL, NULL, NULL}
294
 };
387
 };
295
 
388
 

Notiek ielāde…
Atcelt
Saglabāt