DEV Community

Can Gulmez
Can Gulmez

Posted on

Embedded Linux Development - Part 6

In this tutorial, I will continue to discuss embedded Linux development with ssh server activation. Previously, I've entered into BeagleBone Black over J1 serial header with a USB-UART converter. In here, I will show that how to enter into it with ssh command.

Firstly, there are two important points that you have to do. I've already did these in previous tutorials. Firstly, I compiled the kernel with USB Gadget module and secondly, I installed openssh-server package into the rootfs. USB gadget module enables the USB connection as the virtual ethernet adapter.

Let's do required settings for both side. Use the J1 serial header again to enter into the BeagleBone Black.

Type the "root" and the password. Also creating a normal user is good practice.

root@can:/# useradd -m -s /bin/bash can
root@can:/# passwd can
root@can:/# usermod -aG sudo can
Enter fullscreen mode Exit fullscreen mode

I've created a user named "can" and set the its password. After that go to the your home directory and create a bash script. I named it as setup-usb-gadget.sh.

root@can:/home/can# ls
setup-usb-gadget.sh
Enter fullscreen mode Exit fullscreen mode

Open and copy this into that:

#!/bin/bash

INTERFACE="usb0"
IP_ADDR="198.168.7.2/24"

# Load the g_ether kernel module that creates the ethernet virtual link.
modprobe g_ether

# Configure the link interface.
ip addr flush dev "$INTERFACE"
ip link set "$INTERFACE" up
ip addr add "$IP_ADDR" dev "$INTERFACE"

# Ensure that SSH is running.
systemctl start ssh
Enter fullscreen mode Exit fullscreen mode

In here, I loaded the g_ether module into the kernel. It's the name of USB gadget module. I will create usb0 interface. After that I set it as "up" and its IP address as "198.168.7.2". You can give any IP address, doesn't matter. But generally, "198.168.7.2" is used. Lastly make sure that ssh server is enabled.

Set the executable permission:

root@can:/home/can# chmod +x ./setup-usb-gadget.sh
Enter fullscreen mode Exit fullscreen mode

And then run it.

root@can:/home/can# ./setup-usb-gadget.sh 
[  644.487501] g_ether gadget.0: HOST MAC f6:b0:84:e3:dc:c2
[  644.493125] g_ether gadget.0: MAC e2:87:7a:43:97:1d
[  644.498588] g_ether gadget.0: Ethernet Gadget, version: Memorial Day 2008
[  644.505565] g_ether gadget.0: g_ether ready
[  644.522283] PM: Cannot get wkup_m3_ipc handle
Enter fullscreen mode Exit fullscreen mode

Lastly, list the available interface on BeagleBone Black:

root@can:/home/can# ip addr show
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
    inet 127.0.0.1/8 scope host lo
       valid_lft forever preferred_lft forever
    inet6 ::1/128 scope host noprefixroute 
       valid_lft forever preferred_lft forever
2: sit0@NONE: <NOARP> mtu 1480 qdisc noop state DOWN group default qlen 1000
    link/sit 0.0.0.0 brd 0.0.0.0
3: eth0: <BROADCAST,MULTICAST> mtu 1500 qdisc noop state DOWN group default qlen 1000
    link/ether 64:8c:bb:f2:25:78 brd ff:ff:ff:ff:ff:ff
4: usb0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP group default qlen 1000
    link/ether e2:87:7a:43:97:1d brd ff:ff:ff:ff:ff:ff
    inet 198.168.7.2/24 brd 198.168.7.255 scope global usb0
       valid_lft forever preferred_lft forever
    inet6 fe80::e087:7aff:fe43:971d/64 scope link 
       valid_lft forever preferred_lft forever
Enter fullscreen mode Exit fullscreen mode

You see the "usb0" interface. That's enough for BeagleBone Black. Let's continue with host side. Open a new terminal and list the available interfaces on host:

can@can:~$ ip addr show
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
    inet 127.0.0.1/8 scope host lo
       valid_lft forever preferred_lft forever
    inet6 ::1/128 scope host noprefixroute 
       valid_lft forever preferred_lft forever
2: enp3s0: <NO-CARRIER,BROADCAST,MULTICAST,UP> mtu 1500 qdisc fq_codel state DOWN group default qlen 1000
    link/ether e8:6a:64:19:45:15 brd ff:ff:ff:ff:ff:ff
3: wlp2s0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue state UP group default qlen 1000
    link/ether b0:fc:36:c1:cf:eb brd ff:ff:ff:ff:ff:ff
    inet 10.152.197.93/24 brd 10.152.197.255 scope global dynamic noprefixroute wlp2s0
       valid_lft 3521sec preferred_lft 3521sec
    inet6 fe80::18fc:91fe:ea80:8fad/64 scope link noprefixroute 
       valid_lft forever preferred_lft forever
4: docker0: <NO-CARRIER,BROADCAST,MULTICAST,UP> mtu 1500 qdisc noqueue state DOWN group default 
    link/ether fa:47:d4:7a:67:3e brd ff:ff:ff:ff:ff:ff
    inet 172.17.0.1/16 brd 172.17.255.255 scope global docker0
       valid_lft forever preferred_lft forever
13: enxf6b084e3dcc2: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc fq_codel state UP group default qlen 1000
    link/ether f6:b0:84:e3:dc:c2 brd ff:ff:ff:ff:ff:ff
Enter fullscreen mode Exit fullscreen mode

BeagleBone Black seems as "enxf6b084e3dcc2" for now. You probably see the different name. It doesn't matter. As wee did in BeagleBone Black, let's do the same things at host side:

can@can:~$ ip addr flush dev enxf6b084e3dcc2
can@can:~$ sudo ip link set enxf6b084e3dcc2 up
can@can:~$ sudo ip addr add 198.168.7.1/24 dev enxf6b084e3dcc2
Enter fullscreen mode Exit fullscreen mode

I assigned the IP address "198.168.7.1" to host (I did "198.168.7.2" for BeagleBone Black).

Lastly, ping BeagleBone Black interface:

can@can:~$ ping 198.168.7.2
PING 198.168.7.2 (198.168.7.2) 56(84) bytes of data.
64 bytes from 198.168.7.2: icmp_seq=1 ttl=64 time=0.904 ms
64 bytes from 198.168.7.2: icmp_seq=2 ttl=64 time=0.351 ms
64 bytes from 198.168.7.2: icmp_seq=3 ttl=64 time=0.449 ms
64 bytes from 198.168.7.2: icmp_seq=4 ttl=64 time=0.478 ms
64 bytes from 198.168.7.2: icmp_seq=5 ttl=64 time=0.585 ms
64 bytes from 198.168.7.2: icmp_seq=6 ttl=64 time=0.477 ms
^C
--- 198.168.7.2 ping statistics ---
6 packets transmitted, 6 received, 0% packet loss, time 5114ms
rtt min/avg/max/mdev = 0.351/0.540/0.904/0.176 ms
Enter fullscreen mode Exit fullscreen mode

That's okey 🥳🥳🥳🥳. You can connect to BeagleBone Black with ssh command for now:

can@can:~$ ssh can@198.168.7.2
can@198.168.7.2's password: 
Linux can 6.14.0-ge8b471285262 #1 SMP Mon Apr 13 12:31:38 +03 2026 armv7l

The programs included with the Debian GNU/Linux system are free software;
the exact distribution terms for each program are described in the
individual files in /usr/share/doc/*/copyright.

Debian GNU/Linux comes with ABSOLUTELY NO WARRANTY, to the extent
permitted by applicable law.
Last login: Sat Jan  1 00:43:51 2000 from 198.168.7.1
can@can:~$ 
can@can:~$ ls
setup-usb-gadget.sh
can@can:~$ cd ..
can@can:/home$ cd ..
can@can:/$ ls
bin  boot  dev  etc  home  lib  lost+found  media  mnt  opt  proc  root  run  sbin  srv  sys  tmp  usr  var
Enter fullscreen mode Exit fullscreen mode

You don't need anymore J1 serial header. You can use it within the ssh terminal for now. Also you can set the setup-usb-gadget.sh as startup script so that it runs automatically after the boot.

In next tutorial, I will inspect the uEnv.txt file and u-boot console. You can make many interesting tricks in there.

Resources:

Simmonds C., Mastering Embedded Linux Programming, Packt Publishing, 2015
Embedded Linux system development training, Bootlin, 2024

Top comments (0)