Linux retrieve monitor names

Tested on Ubuntu 16.04, 18.04. (I know its too late to answer but this solution is relevant today)

$ sudo apt-get install -y hwinfo
...
$ hwinfo --monitor --short
monitor:
                   SONY TV
                   AUO LCD Monitor

I have two monitors attached. One with the laptop and the other is an external display. As soon as the external monitor is plugged-in or out, this command reflects the change. You continuously need to poll. Removing the --short option gives more detailed information.

You can poll the state with the following background job:

$ while true;
>  do
>   hwinfo --monitor --short;
>   sleep 2;
>  done >> monitor.log &

The while true loop runs infinite times. The sleep 2 pauses each iteration of the loop for 2 seconds. And the output of hwinfo --monitor --short is appended to monitor.log. This log file can give you the activity history of monitor plug-in and plug-out.

FYI: I am using a background (daemon) python script using the above command (and other similar ones) to detect if someone is doing some HW plug-ins and plug-outs with the systems in the computer lab. If so, I get appropriate notifications that someone plugged-out/in a monitor, mouse or keyboard in almost real-time!

More info about hwinfo command is here. Its man page is also a good source.


sudo get-edid didn't work for me. (EDIT: now works on another computer, Lubuntu 14.10; I'd blame BIOS differences but that's a random guess...)

Anyway under X, xrandr --verbose prints the EDID block. Here is a quick and dirty way to extract it and pass to parse-edid:

#!/bin/bash
xrandr --verbose | perl -ne '
if ((/EDID(_DATA)?:/.../:/) && !/:/) {
  s/^\s+//;
  chomp;
  $hex .= $_;
} elsif ($hex) {
  # Use "|strings" if you dont have read-edid package installed 
  # and just want to see (or grep) the human-readable parts.
  open FH, "|parse-edid"; 
  print FH pack("H*", $hex); 
  $hex = "";
}'

Inspired by Beni's answer, this will read the EDID data using xrandr and extract the monitors names according to the EDID specification, with no need of any external tools like parse-edid:

#!/bin/bash
while read -r output hex conn; do
    [[ -z "$conn" ]] && conn=${output%%-*}
    echo "# $output $conn   $(xxd -r -p <<< "$hex")"
done < <(xrandr --prop | awk '
    !/^[ \t]/ {
        if (output && hex) print output, hex, conn
        output=$1
        hex=""
    }
    /ConnectorType:/ {conn=$2}
    /[:.]/ && h {
        sub(/.*000000fc00/, "", hex)
        hex = substr(hex, 0, 26) "0a"
        sub(/0a.*/, "", hex)
        h=0
    }
    h {sub(/[ \t]+/, ""); hex = hex $0}
    /EDID.*:/ {h=1}
    END {if (output && hex) print output, hex, conn}
    ' | sort
)

Uses awk to precisely extract the monitor name only, and no extra garbage from the EDID, hence "magic numbers" like 000000fc00, 26 and 0a. Finally uses xxd to convert from hex to ASCII, printing one monitor name per line.

Based on this solution I made a handy script to switch monitors, which can also be used to simply list monitor info:

$ monitor-switch --list
Connected monitors:
# DFP5  HDMI    HT-R391
# DFP7  DVI-I   DELL U2412M

$ monitor-switch --list
Connected monitors:
# DisplayPort-1 DisplayPort DELL U2412M
# DisplayPort-3 DisplayPort DELL U2415
# HDMI-A-2      HDMI        LG TV