Загрузка данных


	/* 4. Main cycle: Прямой стриминг Микрофон -> Динамик */
	while (streaming) {
		void *rx_block = NULL;
		void *tx_block = NULL;
		size_t rx_size;
		int ret;

		/* 1. Читаем данные с микрофона (блокирующий вызов) */
		ret = i2s_read(i2s_dev_rx, &rx_block, &rx_size);
		if (ret < 0) {
			printk("i2s_read failed: %d\n", ret);
			break;
		}

		/* 2. Обрабатываем данные (эффект эхо, если включен) */
		process_block_data(rx_block, SAMPLES_PER_BLOCK_RX);

		/* 3. Выделяем блок памяти для передатчика */
		ret = k_mem_slab_alloc(&mem_slab_tx, &tx_block, K_NO_WAIT);
		if (ret < 0) {
			printk("Failed to allocate TX block: %d\n", ret);
			k_mem_slab_free(&mem_slab_rx, rx_block); // Освобождаем RX буфер!
			break;
		}

		/* 4. Копируем реальные данные микрофона в буфер динамика */
		memcpy(tx_block, rx_block, BLOCK_SIZE_RX);

		/* 5. Освобождаем буфер микрофона СРАЗУ после копирования */
		k_mem_slab_free(&mem_slab_rx, rx_block);

		/* 6. Отправляем данные в динамик */
		ret = i2s_write(i2s_dev_tx, tx_block, BLOCK_SIZE_TX);
		if (ret < 0) {
			printk("i2s_write failed: %d\n", ret);
			k_mem_slab_free(&mem_slab_tx, tx_block);
			break;
		}
	}