技术标签: 5G
本文分析 Free5GC Service request procedure 业务请求流程
UE上下文释放请求过程的目的是由于 NG-RAN 节点的原因,请求 AMF 释放与 UE 相关的逻辑 NG 连接。该过程使用 UE 相关的信令。UE 上下文释放请求消息应指示释放的适当原因值,例如“ TXnRELOCOverall Expiry”,“ Redirection”。
NGAP 消息, Present:NGAPPDUPresentInitiatingMessage,Procedure: ProcedureCodeUEContextReleaseRequest
NGAP.Dispatch
--> HandleUEContextReleaseRequest
如果 ue 在 AMF 状态是已经注册的, PDU 会话资源列表不空,则 SendUpdateSmContextDeactivateUpCnxState 更新上下文 Deactivate 状态
if amfUe.State[ran.AnType].Is(context.Registered) {
Ngaplog.Info("[NGAP] Ue Context in GMM-Registered")
if pDUSessionResourceList != nil {
for _, pduSessionReourceItem := range pDUSessionResourceList.List {
pduSessionID := int32(pduSessionReourceItem.PDUSessionID.Value)
response, _, _, err := consumer.SendUpdateSmContextDeactivateUpCnxState(amfUe, pduSessionID, causeAll)
if err != nil {
logger.NgapLog.Errorf("Send Update SmContextDeactivate UpCnxState Error[%s]", err.Error())
} else if response == nil {
logger.NgapLog.Errorln("Send Update SmContextDeactivate UpCnxState Error")
}
}
}
如果 ue 在 AMF 是未注册,则释放上下文
Ngaplog.Info("[NGAP] Ue Context in Non GMM-Registered")
for pduSessionId := range amfUe.SmContextList {
releaseData := consumer.BuildReleaseSmContextRequest(amfUe, &causeAll, "", nil)
detail, err := consumer.SendReleaseSmContextRequest(amfUe, pduSessionId, releaseData)
if err != nil {
logger.NgapLog.Errorf("Send ReleaseSmContextRequest Error[%s]", err.Error())
} else if detail != nil {
logger.NgapLog.Errorf("Send ReleaseSmContextRequeste Error[%s]", detail.Cause)
}
}
ngap_message.SendUEContextReleaseCommand(ranUe, context.UeContextReleaseUeContext, causeGroup, causeValue)
return
BuildUpdateSmContextRequest 函数更新 SmContextUpdateData,SMF API 为 /sm-contexts/{smContextRef}/modify
func HandlePDUSessionSMContextUpdate(smContextRef string, body models.UpdateSmContextRequest) *http_wrapper.Response {
//GSM State
//PDU Session Modification Reject(Cause Value == 43 || Cause Value != 43)/Complete
//PDU Session Release Command/Complete
logger.PduSessLog.Infoln("In HandlePDUSessionSMContextUpdate")
smContext := smf_context.GetSMContext(smContextRef)
既不包含 N1 也不包含 N2 信息,简单多了,UpCnxState 为 Deactivated
case models.UpCnxState_DEACTIVATED:
if smContext.SMContextState != smf_context.Active {
//Wait till the state becomes Active again
//TODO: implement sleep wait in concurrent architecture
logger.PduSessLog.Infoln("The SMContext State should be Active State")
logger.PduSessLog.Infoln("SMContext state: ", smContext.SMContextState.String())
}
smContext.SMContextState = smf_context.ModificationPending
logger.CtxLog.Traceln("SMContextState Change State: ", smContext.SMContextState.String())
response.JsonData.UpCnxState = models.UpCnxState_DEACTIVATED
smContext.UpCnxState = body.JsonData.UpCnxState
smContext.UeLocation = body.JsonData.UeLocation
// TODO: Deactivate N2 downlink tunnel
//Set FAR and An, N3 Release Info
farList = []*smf_context.FAR{}
smContext.PendingUPF = make(smf_context.PendingUPF)
for _, dataPath := range smContext.Tunnel.DataPathPool {
ANUPF := dataPath.FirstDPNode
DLPDR := ANUPF.DownLinkTunnel.PDR
if DLPDR == nil {
logger.PduSessLog.Errorf("AN Release Error")
} else {
DLPDR.FAR.State = smf_context.RULE_UPDATE
DLPDR.FAR.ApplyAction.Forw = false
DLPDR.FAR.ApplyAction.Buff = true
DLPDR.FAR.ApplyAction.Nocp = true
smContext.PendingUPF[ANUPF.GetNodeIP()] = true
}
farList = append(farList, DLPDR.FAR)
}
sendPFCPModification = true
smContext.SMContextState = smf_context.PFCPModification
logger.CtxLog.Traceln("SMContextState Change State: ", smContext.SMContextState.String())
删除 UE 上下文
Gmm 消息类型设置为 MsgTypeServiceRequest
NGAP 消息设置 Present 为 NGAPPDUPresentInitiatingMessage,ProcedureCode 为 ProcedureCodeInitialUEMessage
func HandleInitialUEMessage(ran *context.AmfRan, message *ngapType.NGAPPDU) {
amfSelf := context.AMF_Self()
var rANUENGAPID *ngapType.RANUENGAPID
var nASPDU *ngapType.NASPDU
var userLocationInformation *ngapType.UserLocationInformation
var rRCEstablishmentCause *ngapType.RRCEstablishmentCause
var fiveGSTMSI *ngapType.FiveGSTMSI
// var aMFSetID *ngapType.AMFSetID
var uEContextRequest *ngapType.UEContextRequest
// var allowedNSSAI *ngapType.AllowedNSSAI
if ranUe == nil {
var err error
ranUe, err = ran.NewRanUe(rANUENGAPID.Value)
if err != nil {
logger.NgapLog.Errorf("NewRanUe Error: %+v", err)
}
Ngaplog.Debugf("New RanUe [RanUeNgapID: %d]", ranUe.RanUeNgapId)
if fiveGSTMSI != nil {
Ngaplog.Debug("Receive 5G-S-TMSI")
servedGuami := amfSelf.ServedGuamiList[0]
// TS 24501 5.6.1
func HandleServiceRequest(ue *context.AmfUe, anType models.AccessType,
serviceRequest *nasMessage.ServiceRequest) error {
logger.GmmLog.Info("Handle Service Reqeust")
if ue == nil {
return fmt.Errorf("AmfUe is nil")
}
util.StopT3513(ue)
util.StopT3565(ue)
SendUpdateSmContextActivateUpCnState 函数向 SMF 发送激活会话上下文请求
if serviceRequest.UplinkDataStatus != nil {
uplinkDataPsi := nasConvert.PSIToBooleanArray(serviceRequest.UplinkDataStatus.Buffer)
reactivationResult = new([16]bool)
for pduSessionId, smContext := range ue.SmContextList {
if pduSessionId == targetPduSessionId {
continue
}
if uplinkDataPsi[pduSessionId] && smContext.PduSessionContext.AccessType == models.AccessType__3_GPP_ACCESS {
response, errRes, _, err := consumer.SendUpdateSmContextActivateUpCnxState(
ue, pduSessionId, models.AccessType__3_GPP_ACCESS)
func HandlePDUSessionSMContextUpdate(smContextRef string, body models.UpdateSmContextRequest) *http_wrapper.Response {
//GSM State
//PDU Session Modification Reject(Cause Value == 43 || Cause Value != 43)/Complete
//PDU Session Release Command/Complete
logger.PduSessLog.Infoln("In HandlePDUSessionSMContextUpdate")
smContext := smf_context.GetSMContext(smContextRef)
根据 N2 会话信息类型为 N2SmInfoType_PDU_RES_SETUP_RSP
switch smContextUpdateData.N2SmInfoType {
case models.N2SmInfoType_PDU_RES_SETUP_RSP:
if smContext.SMContextState != smf_context.Active {
//Wait till the state becomes Active again
//TODO: implement sleep wait in concurrent architecture
logger.PduSessLog.Infoln("The SMContext State should be Active State")
logger.PduSessLog.Infoln("SMContext state: ", smContext.SMContextState.String())
}
smContext.SMContextState = smf_context.ModificationPending
logger.CtxLog.Traceln("SMContextState Change State: ", smContext.SMContextState.String())
pdrList = []*smf_context.PDR{}
farList = []*smf_context.FAR{}
SMF 向 UPF 发送 PFCP Session Modification Request 将 N3 RAN 与 UPF 建立 GTP 隧道
根据 PDU 会话资源列表更新发向 SMF,这里不分析了,还有 SMF 向 UPF 更新
if pDUSessionResourceSetupResponseList != nil {
Ngaplog.Trace("[NGAP] Send PDUSessionResourceSetupResponseTransfer to SMF")
for _, item := range pDUSessionResourceSetupResponseList.List {
pduSessionID := int32(item.PDUSessionID.Value)
transfer := item.PDUSessionResourceSetupResponseTransfer
// response, _, _, err := consumer.SendUpdateSmContextN2Info(amfUe, pduSessionID,
_, _, _, err := consumer.SendUpdateSmContextN2Info(amfUe, pduSessionID,
models.N2SmInfoType_PDU_RES_SETUP_RSP, transfer)
if err != nil {
Ngaplog.Errorf("SendUpdateSmContextN2Info[PDUSessionResourceSetupResponseTransfer] Error:\n%s", err.Error())
}
// RAN initiated QoS Flow Mobility in subclause 5.2.2.3.7
// if response != nil && response.BinaryDataN2SmInformation != nil {
// TODO: n2SmInfo send to RAN
// } else if response == nil {
// TODO: error handling
// }
}
}
文章浏览阅读240次。20172319 2018.10.19 《Java程序设计教程》第7周课堂实践课程:《程序设计与数据结构》班级:1723学生:唐才铭学号:20172319指导老师:王志强日期:2018.10.19必修/选修:必修目录测试内容测试要求实验步骤需求分析相关知识实现及解释错误分析参考资料测试内容三种查找算法练习:给定关键字序列:11,..._第六次作业 92给定关键字序列{ 11,78, 10, 1,3,2,4,21},分别用顺序查找、折半查找
文章浏览阅读290次。jobs------------查看在后台执行的进程fg %n----------将后台执行进程n调到前台执行,n表示jobnumber(通过jobs查看的进程编号,而非pid)ctrl+z----------将在前台执行的进程,放到后台并挂起bg %n---------将在后台挂起的进程,继续执行ctrl+c----------前台进程终止kill %n---------杀掉后台运行的..._jjob命令
文章浏览阅读9.6k次,点赞128次,收藏118次。本文为经典算法OJ题练习,大部分题型都有多种思路,每种思路的解法博主都试过了(去网站那里验证)是正确的,大家可以参考!!
文章浏览阅读1.5k次。思路简单粗暴,直接注册一个模块监听,然后当目标驱动加载时hook它的驱动加载函数,直接返回成功,对付一下比较简单的驱动保护效果屡试不爽获取DriverEntryPVOID GetDriverEntryByImageBase(PVOID ImageBase){ PIMAGE_DOS_HEADER pDOSHeader; PIMAGE_NT_HEADERS64 pNTHeader; PVOID pEntryPoint; pDOSHeader = (PIMAGE_DOS_HEADER)ImageB_pimage_nt_headers64 pntheaders64 = (pimage_nt_headers64)((ulong64)hmod + pdo
文章浏览阅读7.1k次,点赞6次,收藏9次。在SpringBoot中为了降低耦合度,简化开发,有很多方便的注解,其中@COnfigurationProperties和@ConditionalOnProperties就只个人觉得比较好用的组件中的两个@ConfigurationProperties的用法这个注解可以根据配置文件中的配置绑定相关属性到有这个注解的类上其中有四个静态方法 @AliasFor("prefix") Stri..._configurationonproperties
文章浏览阅读2.6k次。标注、批注_visio标注总跑到图形中心
文章浏览阅读232次。方法没有重载在其他语言中,可以定义多个重名的方法,只要保证方法签名唯一即可。方法签名包含三个部分:方法名、参数数量、参数类型。Python中,方法的参数没有类型(调用时确定参数类型),参数的数量也可以由可变参数控制。因此,Python方法中是没有方法重载的。定义一个方法即可有多种调用方式。相当于实现了其他语言中的方法的重载。如果我们在类体中定义了多个重名的方法,只有最后一个方法有效。建议: 不要使用重名的方法,Python中方法没有重载。class Person: def say_hi(s
文章浏览阅读695次。点击查看原文更多精彩内容由于2016年年中调换工作的原因,对容器网络的研究中断过一段时间。随着当前项目对Kubernetes应用的深入,我感觉之前对于容器网络的粗浅理解已经不够了,容器网络成了摆在前面的“一道坎”。继续深入理解K8s网络、容器网络已经势在必行。而这篇文章就算是一个重新开始,也是对之前浅表理解的一个补充。我还是先从Docker容器网络入手,虽然Dock_veth addrgenmode
文章浏览阅读1w次,点赞10次,收藏48次。一、PE的基本概念 PE(Portable Execute)文件是Windows下可执行文件的总称,常见的有DLL,EXE,OCX,SYS等,事实上,一个文件是否是PE文件与其扩展名无关,PE文件可以是任何扩展名。 认识PE文件不是作为单一内存映射文件被装入内存是很重要的。Windows加载器(又称PE加载器)遍历PE文件并决定文件的哪一部分被映射,这种映射方式是将文件较高的偏移..._pe文件头作用
文章浏览阅读2.6w次,点赞3次,收藏27次。Charles安装教程1、解压文件包之后双击打开“Charles 64位_4.2.7.4.msi”开始安装2、点击“Next”3、勾选“我同意条款”,然后点击“Next”4、选择软件要安装的目录,然后点击“Next”5、点击“Install”6、点击“Finish”完成安装教程1、我们打开“Charles 汉化&授权.exe”,选择“中文注册版”,然后点击“Patch”即可。资源地址:Charles(HTTP抓包工具软件)中文版Charles使用教程1、PC抓包由于该_charles中文版
文章浏览阅读627次,点赞28次,收藏23次。本系统采用的数据库是Mysql,使用python语言,使用django技术进行开发。在设计过程中,充分保证了系统代码的良好可读性、实用性、易扩展性、通用性、便于后期维护、操作方便以及页面简洁等特点。
文章浏览阅读956次。Ansible架构图_centos 安装 ansible 国内源