1*fd71220bSRobert Mustacchi /*
2*fd71220bSRobert Mustacchi * This file and its contents are supplied under the terms of the
3*fd71220bSRobert Mustacchi * Common Development and Distribution License ("CDDL"), version 1.0.
4*fd71220bSRobert Mustacchi * You may only use this file in accordance with the terms of version
5*fd71220bSRobert Mustacchi * 1.0 of the CDDL.
6*fd71220bSRobert Mustacchi *
7*fd71220bSRobert Mustacchi * A full copy of the text of the CDDL should have accompanied this
8*fd71220bSRobert Mustacchi * source. A copy of the CDDL is also available via the Internet at
9*fd71220bSRobert Mustacchi * http://www.illumos.org/license/CDDL.
10*fd71220bSRobert Mustacchi */
11*fd71220bSRobert Mustacchi
12*fd71220bSRobert Mustacchi /*
13*fd71220bSRobert Mustacchi * Copyright 2022 Oxide Computer Company
14*fd71220bSRobert Mustacchi */
15*fd71220bSRobert Mustacchi
16*fd71220bSRobert Mustacchi /*
17*fd71220bSRobert Mustacchi * Our goal is to create the /dev/dpio/%s links that need to exist for each
18*fd71220bSRobert Mustacchi * dpio(7) related entry. The kgpio driver creates a minor node for each dpio of
19*fd71220bSRobert Mustacchi * the form 'dpio:<name>' and uses the type DDI_NT_GPIO_DPIO. For exmaple, the
20*fd71220bSRobert Mustacchi * name 'dpio:foobar' would cause us to create /dev/dpio/foobar.
21*fd71220bSRobert Mustacchi */
22*fd71220bSRobert Mustacchi
23*fd71220bSRobert Mustacchi #include <devfsadm.h>
24*fd71220bSRobert Mustacchi #include <string.h>
25*fd71220bSRobert Mustacchi
26*fd71220bSRobert Mustacchi static int
dpio_link(di_minor_t minor,di_node_t node)27*fd71220bSRobert Mustacchi dpio_link(di_minor_t minor, di_node_t node)
28*fd71220bSRobert Mustacchi {
29*fd71220bSRobert Mustacchi const char *name, *colon;
30*fd71220bSRobert Mustacchi char buf[PATH_MAX];
31*fd71220bSRobert Mustacchi
32*fd71220bSRobert Mustacchi name = di_minor_name(minor);
33*fd71220bSRobert Mustacchi if (name == NULL) {
34*fd71220bSRobert Mustacchi return (DEVFSADM_CONTINUE);
35*fd71220bSRobert Mustacchi }
36*fd71220bSRobert Mustacchi
37*fd71220bSRobert Mustacchi colon = strchr(name, ':');
38*fd71220bSRobert Mustacchi if (colon == NULL) {
39*fd71220bSRobert Mustacchi return (DEVFSADM_CONTINUE);
40*fd71220bSRobert Mustacchi }
41*fd71220bSRobert Mustacchi
42*fd71220bSRobert Mustacchi if (snprintf(buf, sizeof (buf), "dpio/%s", colon + 1) < sizeof (buf)) {
43*fd71220bSRobert Mustacchi (void) devfsadm_mklink(buf, node, minor, 0);
44*fd71220bSRobert Mustacchi }
45*fd71220bSRobert Mustacchi
46*fd71220bSRobert Mustacchi return (DEVFSADM_CONTINUE);
47*fd71220bSRobert Mustacchi }
48*fd71220bSRobert Mustacchi
49*fd71220bSRobert Mustacchi static devfsadm_create_t dpio_create_cbt[] = {
50*fd71220bSRobert Mustacchi { "pseudo", DDI_NT_GPIO_DPIO, "kgpio", TYPE_EXACT | DRV_EXACT, ILEVEL_0,
51*fd71220bSRobert Mustacchi dpio_link }
52*fd71220bSRobert Mustacchi };
53*fd71220bSRobert Mustacchi
54*fd71220bSRobert Mustacchi static devfsadm_remove_t dpio_remove_cbt[] = {
55*fd71220bSRobert Mustacchi { "pseudo", "^dpio/[A-Za-z0-9]+$", RM_POST | RM_HOT | RM_ALWAYS,
56*fd71220bSRobert Mustacchi ILEVEL_0, devfsadm_rm_all },
57*fd71220bSRobert Mustacchi };
58*fd71220bSRobert Mustacchi
59*fd71220bSRobert Mustacchi DEVFSADM_CREATE_INIT_V0(dpio_create_cbt);
60*fd71220bSRobert Mustacchi DEVFSADM_REMOVE_INIT_V0(dpio_remove_cbt);
61