Received: by 2002:a6b:500f:0:0:0:0:0 with SMTP id e15csp4726153iob; Sun, 8 May 2022 23:24:24 -0700 (PDT) X-Google-Smtp-Source: ABdhPJzD1dGUeF6BLclAu9uOOSf3GZpCG3CQcUrGCbSqlhV5zU7G8FWdT+eml7crluc2fub3o+wp X-Received: by 2002:a17:90b:3a8b:b0:1dc:4eb4:1f2a with SMTP id om11-20020a17090b3a8b00b001dc4eb41f2amr25141199pjb.50.1652077463889; Sun, 08 May 2022 23:24:23 -0700 (PDT) ARC-Seal: i=1; a=rsa-sha256; t=1652077463; cv=none; d=google.com; s=arc-20160816; b=oUChuJYozA7/q7rgfI8pqdLNPOFgmd7QLir+B1ibe7hpYz0v615soJhrFSL6lFVjKU v04M3Mgqop1lOj/4ALeinAptapwEtyPSdY7oSN0FK5ve0o++pfwsAbvwBLqQBQsz+wdu 2ESfp5YVQDOIr0X61wuYVvA0mkiyCVhbHYYUUCpfdO6V2dKX2fJFDDPasuR0T5vzFF3s s+JOLkYrSp6vSIRCprUGazuQbDGn1/RaKGJWZDrQOuoNrj6qyoKXdczLKufboaN6ANWy psFngRSUE3EvZEswig8CTiJpH6XLuWEsT5kZ0sWLleh8PzkGWC9esbmFwSjRR0595LFM LDVQ== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20160816; h=list-id:precedence:content-transfer-encoding:mime-version :user-agent:references:in-reply-to:message-id:date:subject:cc:to :from:dkim-signature; bh=kCUQrrFNIQ72kesmDbGb7YV4fYfdmCQSqC4jbEBgjsg=; b=fmZII9Sa8IrTvjQz093YdWXbQs3o969qNU+YQE1mmNR4adrXq+fRhLXMuKvAil9bAO /KdXqTChWRrjainiFqVP8noEKeuXDiG9gbjdqBFW97QD33Zw4GseYFdeFiD0EnutD4st hWhmoaAmQqix2fBQ/aRj/2hkSRao8doIpKqIDTKZpxVps5379wCF5irKkqKrMotnpiKY 4CUikoTwqCDPuyE78PUrYT4sTA+T7bI+KbFimEQdayuGvZhmXnJXjEJ9H+ArcnxWTrdT AkDQXffAqVHnOKdW+P8L9U2eIIPvoIGCK+/cAffLEjhyvlhjxNcuwHlUqkg+2fbOweOp qRYQ== ARC-Authentication-Results: i=1; mx.google.com; dkim=pass header.i=@linuxfoundation.org header.s=korg header.b=Z6++IPWz; spf=softfail (google.com: domain of transitioning linux-kernel-owner@vger.kernel.org does not designate 23.128.96.19 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org; dmarc=pass (p=NONE sp=NONE dis=NONE) header.from=linuxfoundation.org Return-Path: Received: from lindbergh.monkeyblade.net (lindbergh.monkeyblade.net. [23.128.96.19]) by mx.google.com with ESMTPS id d139-20020a621d91000000b004fa3a8dffd1si12335408pfd.136.2022.05.08.23.24.22 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Sun, 08 May 2022 23:24:23 -0700 (PDT) Received-SPF: softfail (google.com: domain of transitioning linux-kernel-owner@vger.kernel.org does not designate 23.128.96.19 as permitted sender) client-ip=23.128.96.19; Authentication-Results: mx.google.com; dkim=pass header.i=@linuxfoundation.org header.s=korg header.b=Z6++IPWz; spf=softfail (google.com: domain of transitioning linux-kernel-owner@vger.kernel.org does not designate 23.128.96.19 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org; dmarc=pass (p=NONE sp=NONE dis=NONE) header.from=linuxfoundation.org Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by lindbergh.monkeyblade.net (Postfix) with ESMTP id 1F09C8CB3C; Sun, 8 May 2022 23:21:16 -0700 (PDT) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1358244AbiEDR3v (ORCPT + 99 others); Wed, 4 May 2022 13:29:51 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:40792 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1356649AbiEDRJh (ORCPT ); Wed, 4 May 2022 13:09:37 -0400 Received: from ams.source.kernel.org (ams.source.kernel.org [IPv6:2604:1380:4601:e00::1]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id A7A4949FB4; Wed, 4 May 2022 09:55:17 -0700 (PDT) Received: from smtp.kernel.org (relay.kernel.org [52.25.139.140]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by ams.source.kernel.org (Postfix) with ESMTPS id 50C8BB8278E; Wed, 4 May 2022 16:55:16 +0000 (UTC) Received: by smtp.kernel.org (Postfix) with ESMTPSA id 04212C385A5; Wed, 4 May 2022 16:55:14 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=linuxfoundation.org; s=korg; t=1651683315; bh=DusKGaS4SC6aIyCCQNClYmGsE+SaM+XUOsobTQzBos4=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=Z6++IPWzKz1v8EpfFpf3fKwhph+ZpHHQUDCAwm136qaAmiZSyYi799/2EDwzLx9Df 1YMbEa1t5YQblrS5uX4pzSVpI/1cPJ5A+t1H6qEwSz5BHPh6SW7ntG1eovWjMbN21s Jz+tGDImWCqV7o3uvq/kUx8+y6xXpJ+KiXdiLcd8= From: Greg Kroah-Hartman To: linux-kernel@vger.kernel.org Cc: Greg Kroah-Hartman , stable@vger.kernel.org, Daniel Starke Subject: [PATCH 5.15 157/177] tty: n_gsm: fix restart handling via CLD command Date: Wed, 4 May 2022 18:45:50 +0200 Message-Id: <20220504153107.482892453@linuxfoundation.org> X-Mailer: git-send-email 2.36.0 In-Reply-To: <20220504153053.873100034@linuxfoundation.org> References: <20220504153053.873100034@linuxfoundation.org> User-Agent: quilt/0.66 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit X-Spam-Status: No, score=-2.6 required=5.0 tests=BAYES_00,DKIMWL_WL_HIGH, DKIM_SIGNED,DKIM_VALID,DKIM_VALID_AU,HEADER_FROM_DIFFERENT_DOMAINS, MAILING_LIST_MULTI,RDNS_NONE,SPF_HELO_NONE,T_SCC_BODY_TEXT_LINE autolearn=unavailable autolearn_force=no version=3.4.6 X-Spam-Checker-Version: SpamAssassin 3.4.6 (2021-04-09) on lindbergh.monkeyblade.net Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org From: Daniel Starke commit aa371e96f05dcb36a88298f5cb70aa7234d5e8b8 upstream. n_gsm is based on the 3GPP 07.010 and its newer version is the 3GPP 27.010. See https://portal.3gpp.org/desktopmodules/Specifications/SpecificationDetails.aspx?specificationId=1516 The changes from 07.010 to 27.010 are non-functional. Therefore, I refer to the newer 27.010 here. Chapter 5.8.2 states that both sides will revert to the non-multiplexed mode via a close-down message (CLD). The usual program flow is as following: - start multiplex mode by sending AT+CMUX to the mobile - establish the control channel (DLCI 0) - establish user channels (DLCI >0) - terminate user channels - send close-down message (CLD) - revert to AT protocol (i.e. leave multiplexed mode) The AT protocol is out of scope of the n_gsm driver. However, gsm_disconnect() sends CLD if gsm_config() detects that the requested parameters require the mux protocol to restart. The next immediate action is to start the mux protocol by opening DLCI 0 again. Any responder side which handles CLD commands correctly forces us to fail at this point because AT+CMUX needs to be sent to the mobile to start the mux again. Therefore, remove the CLD command in this phase and keep both sides in multiplexed mode. Remove the gsm_disconnect() function as it become unnecessary and merge the remaining parts into gsm_cleanup_mux() to handle the termination order and locking correctly. Fixes: 71e077915396 ("tty: n_gsm: do not send/receive in ldisc close path") Cc: stable@vger.kernel.org Signed-off-by: Daniel Starke Link: https://lore.kernel.org/r/20220414094225.4527-2-daniel.starke@siemens.com Signed-off-by: Greg Kroah-Hartman --- drivers/tty/n_gsm.c | 68 +++++++++++++++------------------------------------- 1 file changed, 20 insertions(+), 48 deletions(-) --- a/drivers/tty/n_gsm.c +++ b/drivers/tty/n_gsm.c @@ -2048,49 +2048,35 @@ static void gsm_error(struct gsm_mux *gs gsm->io_error++; } -static int gsm_disconnect(struct gsm_mux *gsm) -{ - struct gsm_dlci *dlci = gsm->dlci[0]; - struct gsm_control *gc; - - if (!dlci) - return 0; - - /* In theory disconnecting DLCI 0 is sufficient but for some - modems this is apparently not the case. */ - gc = gsm_control_send(gsm, CMD_CLD, NULL, 0); - if (gc) - gsm_control_wait(gsm, gc); - - del_timer_sync(&gsm->t2_timer); - /* Now we are sure T2 has stopped */ - - gsm_dlci_begin_close(dlci); - wait_event_interruptible(gsm->event, - dlci->state == DLCI_CLOSED); - - if (signal_pending(current)) - return -EINTR; - - return 0; -} - /** * gsm_cleanup_mux - generic GSM protocol cleanup * @gsm: our mux + * @disc: disconnect link? * * Clean up the bits of the mux which are the same for all framing * protocols. Remove the mux from the mux table, stop all the timers * and then shut down each device hanging up the channels as we go. */ -static void gsm_cleanup_mux(struct gsm_mux *gsm) +static void gsm_cleanup_mux(struct gsm_mux *gsm, bool disc) { int i; struct gsm_dlci *dlci = gsm->dlci[0]; struct gsm_msg *txq, *ntxq; gsm->dead = true; + mutex_lock(&gsm->mutex); + + if (dlci) { + if (disc && dlci->state != DLCI_CLOSED) { + gsm_dlci_begin_close(dlci); + wait_event(gsm->event, dlci->state == DLCI_CLOSED); + } + dlci->dead = true; + } + + /* Finish outstanding timers, making sure they are done */ + del_timer_sync(&gsm->t2_timer); spin_lock(&gsm_mux_lock); for (i = 0; i < MAX_MUX; i++) { @@ -2104,13 +2090,7 @@ static void gsm_cleanup_mux(struct gsm_m if (i == MAX_MUX) return; - del_timer_sync(&gsm->t2_timer); - /* Now we are sure T2 has stopped */ - if (dlci) - dlci->dead = true; - /* Free up any link layer users */ - mutex_lock(&gsm->mutex); for (i = 0; i < NUM_DLCI; i++) if (gsm->dlci[i]) gsm_dlci_release(gsm->dlci[i]); @@ -2312,19 +2292,11 @@ static int gsm_config(struct gsm_mux *gs /* * Close down what is needed, restart and initiate the new - * configuration + * configuration. On the first time there is no DLCI[0] + * and closing or cleaning up is not necessary. */ - - if (need_close || need_restart) { - int ret; - - ret = gsm_disconnect(gsm); - - if (ret) - return ret; - } - if (need_restart) - gsm_cleanup_mux(gsm); + if (need_close || need_restart) + gsm_cleanup_mux(gsm, true); gsm->initiator = c->initiator; gsm->mru = c->mru; @@ -2433,7 +2405,7 @@ static void gsmld_detach_gsm(struct tty_ WARN_ON(tty != gsm->tty); for (i = 1; i < NUM_DLCI; i++) tty_unregister_device(gsm_tty_driver, base + i); - gsm_cleanup_mux(gsm); + gsm_cleanup_mux(gsm, false); tty_kref_put(gsm->tty); gsm->tty = NULL; } @@ -2536,7 +2508,7 @@ static int gsmld_open(struct tty_struct ret = gsmld_attach_gsm(tty, gsm); if (ret != 0) { - gsm_cleanup_mux(gsm); + gsm_cleanup_mux(gsm, false); mux_put(gsm); } return ret;