summarylogtreecommitdiffstats
path: root/udev.sh
blob: 8d527eb3ae6bf5e573beabe2acfd54db1f98458f (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
#!/bin/sh
# Copyright (c) 2016 - 2020 DisplayLink (UK) Ltd.
# File autogenerated by udev-installer.sh script

get_displaylink_dev_count()
{
   cat /sys/bus/usb/devices/*/idVendor | grep 17e9 | wc -l
}

get_displaylink_symlink_count()
{
  root=$1

  if [ ! -d "$root/displaylink/by-id" ]; then
    echo "0"
    return
  fi

  for f in $(find $root/displaylink/by-id -type l -exec realpath {} \; 2> /dev/null); do
    test -c $f && echo $f;
  done | wc -l
}

start_displaylink()
{
  if [ "$(get_displaylink_dev_count)" != "0" ]; then
    start_service
  fi
}

stop_displaylink()
{
  root=$1

  if [ "$(get_displaylink_symlink_count $root)" = "0" ]; then
    stop_service
  fi
}

remove_dldir_if_empty()
{
  root=$1
  (cd $root; rmdir -p --ignore-fail-on-non-empty displaylink/by-id)
}

create_displaylink_symlink()
{
  root=$1
  device_id=$2
  devnode=$3

  mkdir -p $root/displaylink/by-id
  ln -sf $devnode $root/displaylink/by-id/$device_id
}

unlink_displaylink_symlink()
{
   root=$1
   devname=$2

   for f in $root/displaylink/by-id/*; do
     if [ ! -e "$f" ] || ([ -L "$f" ] && [ "$f" -ef "$devname" ]); then
       unlink "$f"
     fi
   done
   (cd $root; rmdir -p --ignore-fail-on-non-empty displaylink/by-id)
}

prune_broken_links()
{
  root=$1

  dir="$root/displaylink/by-id"
  find -L "$dir" -name "$dir" -o type d -prune -o -type -l -exec rm {} +
  remove_dldir_if_empty $root
}

disable_u1_u2()
{
    echo 0 > "/sys$1/../port/usb3_lpm_permit"
}

main()
{
  action=$1
  root=$2
  devpath=$3
  devnode=$5

  if [ "$action" = "add" ]; then
    device_id=$4
    create_displaylink_symlink $root $device_id $devnode
    start_displaylink
    disable_u1_u2 "$devpath"
  elif [ "$action" = "remove" ]; then
      devname=$3
      unlink_displaylink_symlink "$root" "$devname"
      stop_displaylink "$root"
  elif [ "$action" = "START" ]; then
    start_displaylink
  fi
}

start_service()
{
  systemctl start --no-block displaylink
}

stop_service()
{
  systemctl stop displaylink
}

case "$ACTION" in
  add)
    if [ "$#" -ge 3 ]; then
      main $ACTION $1 $2 $3 $4
      return 0
    elif [ "$#" -ge 2 ]; then
      start_displaylink
      return 0
    fi ;;
  remove)
    if [ "$#" -ge 2 ]; then
      main $ACTION $1 $2 $3
      return 0
    else
      prune_broken_links $root
      return 0
    fi ;;
esac