aboutsummaryrefslogtreecommitdiff
path: root/examples/rp235x/src/bin/ethernet_w5500_tcp_client.rs
diff options
context:
space:
mode:
Diffstat (limited to 'examples/rp235x/src/bin/ethernet_w5500_tcp_client.rs')
-rw-r--r--examples/rp235x/src/bin/ethernet_w5500_tcp_client.rs127
1 files changed, 127 insertions, 0 deletions
diff --git a/examples/rp235x/src/bin/ethernet_w5500_tcp_client.rs b/examples/rp235x/src/bin/ethernet_w5500_tcp_client.rs
new file mode 100644
index 000000000..b726b9cc6
--- /dev/null
+++ b/examples/rp235x/src/bin/ethernet_w5500_tcp_client.rs
@@ -0,0 +1,127 @@
1//! This example implements a TCP client that attempts to connect to a host on port 1234 and send it some data once per second.
2//!
3//! Example written for the [`WIZnet W5500-EVB-Pico2`](https://docs.wiznet.io/Product/iEthernet/W5500/w5500-evb-pico2) board.
4
5#![no_std]
6#![no_main]
7
8use core::str::FromStr;
9
10use defmt::*;
11use embassy_executor::Spawner;
12use embassy_futures::yield_now;
13use embassy_net::{Stack, StackResources};
14use embassy_net_wiznet::chip::W5500;
15use embassy_net_wiznet::*;
16use embassy_rp::clocks::RoscRng;
17use embassy_rp::gpio::{Input, Level, Output, Pull};
18use embassy_rp::peripherals::SPI0;
19use embassy_rp::spi::{Async, Config as SpiConfig, Spi};
20use embassy_time::{Delay, Duration, Timer};
21use embedded_hal_bus::spi::ExclusiveDevice;
22use embedded_io_async::Write;
23use static_cell::StaticCell;
24use {defmt_rtt as _, panic_probe as _};
25
26#[embassy_executor::task]
27async fn ethernet_task(
28 runner: Runner<
29 'static,
30 W5500,
31 ExclusiveDevice<Spi<'static, SPI0, Async>, Output<'static>, Delay>,
32 Input<'static>,
33 Output<'static>,
34 >,
35) -> ! {
36 runner.run().await
37}
38
39#[embassy_executor::task]
40async fn net_task(mut runner: embassy_net::Runner<'static, Device<'static>>) -> ! {
41 runner.run().await
42}
43
44#[embassy_executor::main]
45async fn main(spawner: Spawner) {
46 let p = embassy_rp::init(Default::default());
47 let mut rng = RoscRng;
48 let mut led = Output::new(p.PIN_25, Level::Low);
49
50 let mut spi_cfg = SpiConfig::default();
51 spi_cfg.frequency = 50_000_000;
52 let (miso, mosi, clk) = (p.PIN_16, p.PIN_19, p.PIN_18);
53 let spi = Spi::new(p.SPI0, clk, mosi, miso, p.DMA_CH0, p.DMA_CH1, spi_cfg);
54 let cs = Output::new(p.PIN_17, Level::High);
55 let w5500_int = Input::new(p.PIN_21, Pull::Up);
56 let w5500_reset = Output::new(p.PIN_20, Level::High);
57
58 let mac_addr = [0x02, 0x00, 0x00, 0x00, 0x00, 0x00];
59 static STATE: StaticCell<State<8, 8>> = StaticCell::new();
60 let state = STATE.init(State::<8, 8>::new());
61 let (device, runner) = embassy_net_wiznet::new(
62 mac_addr,
63 state,
64 ExclusiveDevice::new(spi, cs, Delay),
65 w5500_int,
66 w5500_reset,
67 )
68 .await
69 .unwrap();
70 unwrap!(spawner.spawn(ethernet_task(runner)));
71
72 // Generate random seed
73 let seed = rng.next_u64();
74
75 // Init network stack
76 static RESOURCES: StaticCell<StackResources<3>> = StaticCell::new();
77 let (stack, runner) = embassy_net::new(
78 device,
79 embassy_net::Config::dhcpv4(Default::default()),
80 RESOURCES.init(StackResources::new()),
81 seed,
82 );
83
84 // Launch network task
85 unwrap!(spawner.spawn(net_task(runner)));
86
87 info!("Waiting for DHCP...");
88 let cfg = wait_for_config(stack).await;
89 let local_addr = cfg.address.address();
90 info!("IP address: {:?}", local_addr);
91
92 let mut rx_buffer = [0; 4096];
93 let mut tx_buffer = [0; 4096];
94 loop {
95 let mut socket = embassy_net::tcp::TcpSocket::new(stack, &mut rx_buffer, &mut tx_buffer);
96 socket.set_timeout(Some(Duration::from_secs(10)));
97
98 led.set_low();
99 info!("Connecting...");
100 let host_addr = embassy_net::Ipv4Address::from_str("192.168.0.118").unwrap();
101 if let Err(e) = socket.connect((host_addr, 1234)).await {
102 warn!("connect error: {:?}", e);
103 continue;
104 }
105 info!("Connected to {:?}", socket.remote_endpoint());
106 led.set_high();
107
108 let msg = b"Hello world!\n";
109 loop {
110 if let Err(e) = socket.write_all(msg).await {
111 warn!("write error: {:?}", e);
112 break;
113 }
114 info!("txd: {}", core::str::from_utf8(msg).unwrap());
115 Timer::after_secs(1).await;
116 }
117 }
118}
119
120async fn wait_for_config(stack: Stack<'static>) -> embassy_net::StaticConfigV4 {
121 loop {
122 if let Some(config) = stack.config_v4() {
123 return config.clone();
124 }
125 yield_now().await;
126 }
127}