312 lines
11 KiB
Diff
312 lines
11 KiB
Diff
From b7a069a36d6e61977f32b2a24d84899182e38149 Mon Sep 17 00:00:00 2001
|
||
From: liuxinhao <liuxinhao@kylinsec.com.cn>
|
||
Date: Thu, 8 Dec 2022 10:42:44 +0800
|
||
Subject: [PATCH 4/6] fix(SIGTERM Processing): Use socket to notify SIGTERM
|
||
signal, and process SIGTERM signal in the main thread to avoid abnormal exit
|
||
MIME-Version: 1.0
|
||
Content-Type: text/plain; charset=UTF-8
|
||
Content-Transfer-Encoding: 8bit
|
||
|
||
- 使用socket通知SIGTERM信号,在主线程里处理SIGTERM信号,避免非正常退出,修复之前QLightdm::Greeter释放过早导致AuthLightdm调用接口时崩溃问题
|
||
---
|
||
lib/auth-proxy/auth-lightdm.cpp | 24 ++++++-------
|
||
lib/auth-proxy/auth-lightdm.h | 5 +--
|
||
lightdm-greeter/src/greeter-login-window.cpp | 24 ++++++-------
|
||
lightdm-greeter/src/greeter-login-window.h | 3 +-
|
||
lightdm-greeter/src/main.cpp | 37 ++++++++++++++------
|
||
5 files changed, 56 insertions(+), 37 deletions(-)
|
||
|
||
diff --git a/lib/auth-proxy/auth-lightdm.cpp b/lib/auth-proxy/auth-lightdm.cpp
|
||
index 59e7849..e9193e9 100644
|
||
--- a/lib/auth-proxy/auth-lightdm.cpp
|
||
+++ b/lib/auth-proxy/auth-lightdm.cpp
|
||
@@ -16,13 +16,13 @@
|
||
#include "auth-lightdm.h"
|
||
#include <qt5-log-i.h>
|
||
|
||
-AuthLightdm::AuthLightdm(QLightDM::Greeter* greeterAuth, QObject* parent)
|
||
+AuthLightdm::AuthLightdm(QSharedPointer<QLightDM::Greeter> greeterAuth, QObject* parent)
|
||
: AuthBase(parent),
|
||
- m_greeterAuth(greeterAuth)
|
||
+ m_greeterPtrAuth(greeterAuth)
|
||
{
|
||
- connect(m_greeterAuth,&QLightDM::Greeter::showPrompt,this,&AuthLightdm::handleGreeterAuthShowPrompt);
|
||
- connect(m_greeterAuth,&QLightDM::Greeter::showMessage,this,&AuthLightdm::handleGreeterAuthShowMessage);
|
||
- connect(m_greeterAuth,&QLightDM::Greeter::authenticationComplete, this,&AuthLightdm::handleGreeterAuthComplete);
|
||
+ connect(m_greeterPtrAuth.data(),&QLightDM::Greeter::showPrompt,this,&AuthLightdm::handleGreeterAuthShowPrompt);
|
||
+ connect(m_greeterPtrAuth.data(),&QLightDM::Greeter::showMessage,this,&AuthLightdm::handleGreeterAuthShowMessage);
|
||
+ connect(m_greeterPtrAuth.data(),&QLightDM::Greeter::authenticationComplete, this,&AuthLightdm::handleGreeterAuthComplete);
|
||
}
|
||
|
||
AuthLightdm::~AuthLightdm()
|
||
@@ -31,7 +31,7 @@ AuthLightdm::~AuthLightdm()
|
||
|
||
bool AuthLightdm::init()
|
||
{
|
||
- bool bRes = m_greeterAuth->connectSync();
|
||
+ bool bRes = m_greeterPtrAuth->connectSync();
|
||
if( !bRes )
|
||
{
|
||
KLOG_ERROR() << "can't connect greeter auth!";
|
||
@@ -41,33 +41,33 @@ bool AuthLightdm::init()
|
||
|
||
bool AuthLightdm::authenticate(const QString &userName)
|
||
{
|
||
- m_greeterAuth->authenticate(userName);
|
||
+ m_greeterPtrAuth->authenticate(userName);
|
||
return true;
|
||
}
|
||
|
||
void AuthLightdm::cancelAuthentication()
|
||
{
|
||
- m_greeterAuth->cancelAuthentication();
|
||
+ m_greeterPtrAuth->cancelAuthentication();
|
||
}
|
||
|
||
bool AuthLightdm::isAuthenticated() const
|
||
{
|
||
- return m_greeterAuth->isAuthenticated();
|
||
+ return m_greeterPtrAuth->isAuthenticated();
|
||
}
|
||
|
||
bool AuthLightdm::inAuthentication() const
|
||
{
|
||
- return m_greeterAuth->inAuthentication();
|
||
+ return m_greeterPtrAuth->inAuthentication();
|
||
}
|
||
|
||
QString AuthLightdm::authenticationUser() const
|
||
{
|
||
- return m_greeterAuth->authenticationUser();
|
||
+ return m_greeterPtrAuth->authenticationUser();
|
||
}
|
||
|
||
void AuthLightdm::respond(const QString &response)
|
||
{
|
||
- m_greeterAuth->respond(response);
|
||
+ m_greeterPtrAuth->respond(response);
|
||
}
|
||
|
||
void AuthLightdm::handleGreeterAuthShowPrompt(QString text, QLightDM::Greeter::PromptType type)
|
||
diff --git a/lib/auth-proxy/auth-lightdm.h b/lib/auth-proxy/auth-lightdm.h
|
||
index 9451f3c..810c107 100644
|
||
--- a/lib/auth-proxy/auth-lightdm.h
|
||
+++ b/lib/auth-proxy/auth-lightdm.h
|
||
@@ -17,6 +17,7 @@
|
||
|
||
#include "auth-base.h"
|
||
#include <QLightDM/Greeter>
|
||
+#include <QSharedPointer>
|
||
|
||
/**
|
||
* 简单的对QLightDM::Greeter进行了一层包装,只是为了给上层认证代理AuthProxy提供统一的接口
|
||
@@ -25,7 +26,7 @@ class AuthLightdm : public AuthBase
|
||
{
|
||
Q_OBJECT
|
||
public:
|
||
- explicit AuthLightdm(QLightDM::Greeter* greeterAuth, QObject* parent = nullptr);
|
||
+ explicit AuthLightdm(QSharedPointer<QLightDM::Greeter> greeterAuth, QObject* parent = nullptr);
|
||
~AuthLightdm() override;
|
||
|
||
bool init() override;
|
||
@@ -44,7 +45,7 @@ private slots:
|
||
void handleGreeterAuthComplete();
|
||
|
||
private:
|
||
- QLightDM::Greeter* m_greeterAuth;
|
||
+ QSharedPointer<QLightDM::Greeter> m_greeterPtrAuth;
|
||
|
||
};
|
||
|
||
diff --git a/lightdm-greeter/src/greeter-login-window.cpp b/lightdm-greeter/src/greeter-login-window.cpp
|
||
index 9d46662..99beb43 100644
|
||
--- a/lightdm-greeter/src/greeter-login-window.cpp
|
||
+++ b/lightdm-greeter/src/greeter-login-window.cpp
|
||
@@ -86,7 +86,7 @@ bool getIsLoggedIn(const QString &userName)
|
||
GreeterLoginWindow::GreeterLoginWindow(QWidget *parent)
|
||
: QWidget(parent),
|
||
ui(new Ui::GreeterLoginWindow),
|
||
- m_greeter(this),
|
||
+ m_greeterPtr(new QLightDM::Greeter()),
|
||
m_powerMenu(nullptr),
|
||
m_sessionMenu(nullptr),
|
||
m_noListButotnVisiable(true),
|
||
@@ -239,12 +239,12 @@ void GreeterLoginWindow::initUI()
|
||
this, &GreeterLoginWindow::slotUserActivated);
|
||
///自动登录按钮点击
|
||
connect(ui->btn_autologin, &LoginButton::sigClicked, [this]() {
|
||
- m_authProxy->authenticate(m_greeter.autologinUserHint());
|
||
+ m_authProxy->authenticate(m_greeterPtr->autologinUserHint());
|
||
});
|
||
- connect(&m_greeter, &QLightDM::Greeter::autologinTimerExpired, [this]() {
|
||
+ connect(m_greeterPtr.data(), &QLightDM::Greeter::autologinTimerExpired, [this]() {
|
||
//NOTE:修复机器配置了autologin-timeout,但未配置autologin-user的情况
|
||
- if( !m_greeter.autologinUserHint().isEmpty() )
|
||
- m_authProxy->authenticate(m_greeter.autologinUserHint());
|
||
+ if( !m_greeterPtr->autologinUserHint().isEmpty() )
|
||
+ m_authProxy->authenticate(m_greeterPtr->autologinUserHint());
|
||
});
|
||
///重新认证按钮点击
|
||
connect(ui->btn_reAuth, &QPushButton::clicked, [this]() {
|
||
@@ -348,7 +348,7 @@ void GreeterLoginWindow::initMenu()
|
||
|
||
void GreeterLoginWindow::initLightdmGreeter()
|
||
{
|
||
- AuthBase *authInterface = new AuthLightdm(&m_greeter);
|
||
+ AuthBase *authInterface = new AuthLightdm(m_greeterPtr);
|
||
AuthMsgQueue *msgQueue = new AuthMsgQueue();
|
||
|
||
m_authProxy = new AuthProxy(authInterface, this);
|
||
@@ -382,7 +382,7 @@ void GreeterLoginWindow::initLightdmGreeter()
|
||
///用户0->1 且 配置允许显示用户链表 且 当前登录模式为输入用户登录 且 手动登录还未输入用户名并点击确定
|
||
///显示返回按钮
|
||
qInfo() << "rowInserted:" << m_filterModel.rowCount(QModelIndex());
|
||
- if ((m_filterModel.rowCount(QModelIndex()) == 1) && m_showUserList && m_loginMode == LOGIN_MODE_MANUAL && !m_greeter.isAuthenticated())
|
||
+ if ((m_filterModel.rowCount(QModelIndex()) == 1) && m_showUserList && m_loginMode == LOGIN_MODE_MANUAL && !m_greeterPtr->isAuthenticated())
|
||
{
|
||
qInfo() << "setReturn visible true";
|
||
ui->btn_notListAndCancel->setVisible(true);
|
||
@@ -410,12 +410,12 @@ void GreeterLoginWindow::initLightdmGreeter()
|
||
ui->userlist->loadUserList();
|
||
|
||
//NOTE:修复#52982问题,若自动登录用户已存在不自动触发延时自动登录
|
||
- if ( !m_greeter.autologinUserHint().isEmpty() )
|
||
+ if ( !m_greeterPtr->autologinUserHint().isEmpty() )
|
||
{
|
||
- bool isLogged = getIsLoggedIn(m_greeter.autologinUserHint());
|
||
+ bool isLogged = getIsLoggedIn(m_greeterPtr->autologinUserHint());
|
||
if( isLogged )
|
||
{
|
||
- m_greeter.cancelAutologin();
|
||
+ m_greeterPtr->cancelAutologin();
|
||
}
|
||
#if 0
|
||
//WARNING:这种方法不能取得root是否已登录信息
|
||
@@ -551,7 +551,7 @@ void GreeterLoginWindow::startAuthUser(const QString &username, QString userIcon
|
||
ui->label_userName->setText(username);
|
||
ui->loginAvatar->setImage(userIcon);
|
||
|
||
- if (username == m_greeter.autologinUserHint())
|
||
+ if (username == m_greeterPtr->autologinUserHint())
|
||
{
|
||
KLOG_DEBUG() << "authproxy user" << username << "is auto login user,switch to auto login";
|
||
switchToAutoLogin();
|
||
@@ -819,7 +819,7 @@ void GreeterLoginWindow::slotAuthenticationComplete(bool success)
|
||
}
|
||
}
|
||
#endif
|
||
- if (!m_greeter.startSessionSync(m_session))
|
||
+ if (!m_greeterPtr->startSessionSync(m_session))
|
||
{
|
||
KLOG_WARNING() << "start session failed,session:" << m_session;
|
||
}
|
||
diff --git a/lightdm-greeter/src/greeter-login-window.h b/lightdm-greeter/src/greeter-login-window.h
|
||
index 689025e..caf5d63 100644
|
||
--- a/lightdm-greeter/src/greeter-login-window.h
|
||
+++ b/lightdm-greeter/src/greeter-login-window.h
|
||
@@ -23,6 +23,7 @@
|
||
#include <QStateMachine>
|
||
#include <QWidget>
|
||
#include <QWindow>
|
||
+#include <QSharedPointer>
|
||
|
||
#include "auth-define.h"
|
||
#include "auth-msg-queue.h"
|
||
@@ -124,7 +125,7 @@ private:
|
||
|
||
FilterUserProxyModel m_filterModel;
|
||
|
||
- QLightDM::Greeter m_greeter;
|
||
+ QSharedPointer<QLightDM::Greeter> m_greeterPtr;
|
||
QLightDM::UsersModel m_userModel;
|
||
QLightDM::PowerInterface m_powerIface;
|
||
|
||
diff --git a/lightdm-greeter/src/main.cpp b/lightdm-greeter/src/main.cpp
|
||
index 0320c51..e145b1f 100644
|
||
--- a/lightdm-greeter/src/main.cpp
|
||
+++ b/lightdm-greeter/src/main.cpp
|
||
@@ -19,6 +19,8 @@
|
||
#include <QFile>
|
||
#include <QTranslator>
|
||
#include <qt5-log-i.h>
|
||
+#include <sys/socket.h>
|
||
+#include <unistd.h>
|
||
|
||
#include "../../lib/common-widgets/virtual-keyboard.h"
|
||
#include "cursor-helper.h"
|
||
@@ -28,23 +30,27 @@
|
||
#include "scaling-helper.h"
|
||
#include "sync-lock-status.h"
|
||
|
||
+static int sigtermFd[2];
|
||
+
|
||
#define DEFAULT_STYLE_FILE ":/themes/lightdm-kiran-greeter-normal.qss"
|
||
|
||
void termSignalHandler(int unused)
|
||
{
|
||
-#ifdef VIRTUAL_KEYBOARD
|
||
- VirtualKeyboard::instance()->keyboardProcessExit();
|
||
-#endif
|
||
- qApp->quit();
|
||
+ char a = 1;
|
||
+ if(write(sigtermFd[0], &a, sizeof(a)) < 1)
|
||
+ {
|
||
+ qWarning("Failed to handle term signal.");
|
||
+ }
|
||
}
|
||
|
||
void setup_unix_signal_handlers()
|
||
{
|
||
struct sigaction term;
|
||
term.sa_handler = termSignalHandler;
|
||
- sigemptyset(&term.sa_mask);
|
||
term.sa_flags = 0;
|
||
- term.sa_flags |= SA_RESETHAND;
|
||
+ term.sa_flags = SA_RESTART;
|
||
+
|
||
+ sigemptyset(&term.sa_mask);
|
||
int iRet = sigaction(SIGTERM, &term, 0);
|
||
if (iRet != 0)
|
||
{
|
||
@@ -61,9 +67,6 @@ int main(int argc, char *argv[])
|
||
qWarning() << "klog_qt5_init error:" << iRet;
|
||
}
|
||
|
||
- ///安装信号处理
|
||
- setup_unix_signal_handlers();
|
||
-
|
||
///设置缩放比
|
||
double scaled_factor = 0.0;
|
||
switch (KiranGreeterPrefs::instance()->scale_mode())
|
||
@@ -93,6 +96,15 @@ int main(int argc, char *argv[])
|
||
QApplication a(argc, argv);
|
||
QApplication::setAttribute(Qt::AA_UseHighDpiPixmaps);
|
||
|
||
+ // 处理SIGTERM信号
|
||
+ if (::socketpair(AF_UNIX, SOCK_STREAM, 0, sigtermFd))
|
||
+ {
|
||
+ KLOG_WARNING() << "Couldn't create TERM socketpair";
|
||
+ }
|
||
+ QSocketNotifier *snTerm = new QSocketNotifier(sigtermFd[1], QSocketNotifier::Read, &a);
|
||
+ QObject::connect(snTerm, SIGNAL(activated(int)), &a, SLOT(quit()));
|
||
+ setup_unix_signal_handlers();
|
||
+
|
||
///依据登陆器整体缩放比例,设置默认光标大小
|
||
if (!CursorHelper::setDefaultCursorSize(scaled_factor))
|
||
{
|
||
@@ -135,5 +147,10 @@ int main(int argc, char *argv[])
|
||
GreeterScreenManager screenManager;
|
||
screenManager.init();
|
||
|
||
- return a.exec();
|
||
+ int res = a.exec();
|
||
+
|
||
+ close(sigtermFd[0]);
|
||
+ close(sigtermFd[1]);
|
||
+
|
||
+ return res;
|
||
}
|
||
--
|
||
2.33.0
|
||
|