RMI 补充知识

news2024/11/28 18:44:54

0x00 前言

仅作为笔记,对之前的内容进行补充

Registry

Registry是可以单独创建的

LocateRegistry.createRegistry(1099);

实例化RegistryImpl对象

    public static Registry createRegistry(int port) throws RemoteException {
        return new RegistryImpl(port);
    }

创建LiveRef并且将LiveRef封装为UnicastServerRef,然后setup


 public RegistryImpl(int var1) throws RemoteException {
 	//创建 LiveRef
      LiveRef var2 = new LiveRef(id, var1);
	//UnicastServerRef封装LiveRef
      this.setup(new UnicastServerRef(var2));
  }

这里通过exportObject,主要是两个目的,一个是开启soket监听,还有一个就是注册远程类以及创建DGCI

    private void setup(UnicastServerRef var1) throws RemoteException {
        this.ref = var1;
        //调用UnicastServerRef 的exportObject
        var1.exportObject(this, (Object)null, true);
    }

RegistryImpl代理,创建target对象

 public Remote exportObject(Remote var1, Object var2, boolean var3) throws RemoteException {
        Class var4 = var1.getClass();

        Remote var5;
        try {
        		//创建sun.rmi.registry.RegistryImpl代理
            var5 = Util.createProxy(var4, this.getClientRef(), this.forceStubUse);
        } catch (IllegalArgumentException var7) {
            throw new ExportException("remote object implements illegal remote interface", var7);
        }
				//检测接口Remote
        if (var5 instanceof RemoteStub) {
        		
            this.setSkeleton(var1);
        }
		//创建target对象
        Target var6 = new Target(var1, this, var5, this.ref.getObjID(), var3);
        this.ref.exportObject(var6);
        this.hashToMethod_Map = (Map)hashToMethod_Maps.get(var4);
        return var5;
    }

创建代理

public static Remote createProxy(Class<?> var0, RemoteRef var1, boolean var2) throws StubNotFoundException {
        Class var3;
        try {
        		//获取对应的class,会去校验是否是Remote的子类
            var3 = getRemoteClass(var0);
        } catch (ClassNotFoundException var9) {
            throw new StubNotFoundException("object does not implement a remote interface: " + var0.getName());
        }
				//检测withoutStubs中是否包含由类名创建的_Stub组成的内容,
				//如果有则返回false,没有则创建并且返回false
        if (var2 || !ignoreStubClasses && stubClassExists(var3)) {
            return createStub(var3, var1);
        } else {
            ClassLoader var4 = var0.getClassLoader();
            Class[] var5 = getRemoteInterfaces(var0);
            RemoteObjectInvocationHandler var6 = new RemoteObjectInvocationHandler(var1);

            try {
                return (Remote)Proxy.newProxyInstance(var4, var5, var6);
            } catch (IllegalArgumentException var8) {
                throw new StubNotFoundException("unable to create proxy", var8);
            }
        }
    }
private static Class<?> getRemoteClass(Class<?> var0) throws ClassNotFoundException {
        while(var0 != null) {
        // 反射获取接口,create的时候为:sun.rmi.registry.RegistryImpl
            Class[] var1 = var0.getInterfaces();

            for(int var2 = var1.length - 1; var2 >= 0; --var2) {
            //判断是否是Remote.class的子类,是的话直接返回
                if (Remote.class.isAssignableFrom(var1[var2])) {
                    return var0;
                }
            }

            var0 = var0.getSuperclass();
        }

        throw new ClassNotFoundException("class does not implement java.rmi.Remote");
    }
private static RemoteStub createStub(Class<?> var0, RemoteRef var1) throws StubNotFoundException {
				//类名+_Stub
        String var2 = var0.getName() + "_Stub";

        try {
        		//调用输入类的构造方法
            Class var3 = Class.forName(var2, false, var0.getClassLoader());
            Constructor var4 = var3.getConstructor(stubConsParamTypes);
            return (RemoteStub)var4.newInstance(var1);
        } catch (ClassNotFoundException var5) {
            throw new StubNotFoundException("Stub class not found: " + var2, var5);
        } catch (NoSuchMethodException var6) {
            throw new StubNotFoundException("Stub class missing constructor: " + var2, var6);
        } catch (InstantiationException var7) {
            throw new StubNotFoundException("Can't create instance of stub class: " + var2, var7);
        } catch (IllegalAccessException var8) {
            throw new StubNotFoundException("Stub class constructor not public: " + var2, var8);
        } catch (InvocationTargetException var9) {
            throw new StubNotFoundException("Exception creating instance of stub class: " + var2, var9);
        } catch (ClassCastException var10) {
            throw new StubNotFoundException("Stub class not instance of RemoteStub: " + var2, var10);
        }
    }

设置setSkeleton,同时会创建skel

    public void setSkeleton(Remote var1) throws RemoteException {
    		//检测withoutSkeletons是否存在
        if (!withoutSkeletons.containsKey(var1.getClass())) {
            try {
            //不存在则创建类_Skel
                this.skel = Util.createSkeleton(var1);
            } catch (SkeletonNotFoundException var3) {
                withoutSkeletons.put(var1.getClass(), (Object)null);
            }
        }

    }

然后通过exportObject开启socket,并且绑定远程对象,至此,Registry启动完成

public void exportObject(Target var1) throws RemoteException {
        synchronized(this) {
        		//检测socket是否开启
            this.listen();
            ++this.exportCount;
        }

        boolean var2 = false;
        boolean var12 = false;

        try {
            var12 = true;
            //将target绑定到ObjectTable中去
            super.exportObject(var1);
            var2 = true;
            var12 = false;
        } finally {
            if (var12) {
                if (!var2) {
                    synchronized(this) {
                        this.decrementExportCount();
                    }
                }

            }
        }

        if (!var2) {
            synchronized(this) {
                this.decrementExportCount();
            }
        }

    }

DGCI

在创建Registry的时候,生成Target,会同时创建DGCI分布式垃圾回收。
在这里插入图片描述
DGCImpl.class
rt.jar!\sun\rmi\transport\DGCImpl.class

在这里插入图片描述
在创建的DGCImpl_Skel(服务端)中,通过dispatch触发反序列化
在这里插入图片描述

server

通过stub绑定,进行序列化
在这里插入图片描述
然后通过skel进行反序列化

在这里插入图片描述

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/364145.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

IM聊天教程:发送图片/视频/语音/表情

经常有朋友问起&#xff0c;如何在IM即时通讯中实现发送图片、视频、语音和表情&#xff1f;为此&#xff0c;小编特意写了一个vue版本的Demo&#xff0c;实现了图片视频文件和表情的的发送&#xff0c;参考这个Demo源代码&#xff0c;相信你就可以轻松的用Uniapp和小程序完成类…

面向对象的程序设计C++课堂复盘总结 C语言复习+C++基础语法

Stay Hungry&#xff0c;Stay Foolish. 任何人都能写出机器能看懂的代码&#xff0c;但只有优秀的程序员才能写出人能看懂的代码。 有两种写程序的方式&#xff1a;一种是把代码写得非常复杂&#xff0c;以至于 “看不出明显的错误”&#xff1b;另一种是把代码写得非常简单&am…

c/c++开发,无可避免的模板编程实践(篇八)

一、借用标准库模板构造自己的模板 通常&#xff0c;模板设计是遵循当对象的类型不影响类中函数的行为时就使用模板。这也就是为何标准库提供大部分的模板都是与容器、迭代器、适配器、通用算法等有关&#xff0c;因为这些主要是除了对象集合行为&#xff0c;如读写、增删、遍历…

Java ”框架 = 注解 + 反射 + 设计模式“ 之 注解详解

Java ”框架 注解 反射 设计模式“ 之 注解详解 每博一文案 刹那间我真想令时光停住&#xff0c;好让我回顾自己&#xff0c;回顾失去的年华&#xff0c;缅怀哪个穿一身短小的连衣裙 和瘦窄的短衫的小女孩。让我追悔少年时代&#xff0c;我心灵的愚钝无知&#xff0c;它轻易…

oracle11g忘记system密码,重置密码

OPW-00001: 无法打开口令文件 cmd.exe 使用管理员身份登录 找到xxx\product\11.2.0\dbhome_1\database\PWDorcl.ora文件&#xff0c;删除 执行orapwd fileD:\app\product\11.2.0\dbhome_1\database\PWDorcl.ora passwordtiger (orapwd 在\product\11.2.0\dbhome_1\BIN目录下…

DolphinScheduler第一章:环境安装

系列文章目录 DolphinScheduler第一章&#xff1a;环境安装 文章目录系列文章目录前言一、环境准备1.上传文件2.数据库配置3.配置安装文件二、集群部署1.数据部署2.部署 DolphinScheduler3. DolphinScheduler 启停命令总结前言 我们现在开始学习hadoop中的DolphinScheduler组…

Vim 命令速查表

Vim 命令速查表 简介&#xff1a;Vim 命令速查表&#xff0c;注释化 vimrc 配置文件&#xff0c;经典 Vim 键盘图&#xff0c;实用 Vim 书籍&#xff0c;Markdown 格式&#xff0c;目录化检索&#xff0c;系统化学习&#xff0c;快速熟悉使用&#xff01; Vim 官网 | Vim | Vim…

小学生学Arduino---------点阵(三)动态的显示与清除

学习目标&#xff1a; 1、理解“整数值”的概念与使用 2、理解“N1”指令的意义 3、掌握“反复执行多次”指令的使用 4、掌握屏幕模块的清除功能指令 5、理解“反复执行”指令与“反复执行多次”指令的嵌套使用 6、搭建电路图 7、编写程序 效果&#xff1a; 整数包括&#xf…

HTTP cookie格式与约束

cookie是前端编程当中经常要使用到的概念&#xff0c;我们可以使用cookie利用浏览器来存放用户的状态信息保存用户做了一些什么事情。session是服务器端维护的状态。session又是如何和cookie关联起来。后面介绍cookie和session的使用。Cookie 是什么&#xff1f;RFC6265, HTTP …

2022-2023年营销报告(B站平台) | 5大行业势态、流量大盘全景洞察

一直以来&#xff0c;手持高活跃、高粘性用户群体的B站是行业用来观察年轻人消费习惯的重要平台。以至于用户群体的不断壮大带动了B站的商业价值。如今B站的商业舞台越来越大&#xff0c;不断地向外界招手&#xff0c;欢迎更多品牌积极加入到这个千万年轻人聚集的内容社区。为了…

如何使用Kadence Blocks构建迷人的Kadence产品网格

在本教程中&#xff0c;我将逐步教您如何使用 Kadence Blocks 构建一个五列Kadence产品网格&#xff0c;它可以作为全宽区块放置在您的博客文章的顶部。使用这个包含五列的产品网格是在文章顶部展示产品、对每个产品进行简要描述&#xff0c;然后包含一个供用户访问该站点的按钮…

校园社交平台【源码好优多】

简介 本项目是为满足大学生的校园社交需求而设计的&#xff0c;动态模块提供发布/删除/搜索/点赞/收藏/评论动态功能&#xff0c;个人模块提供关注与私信以及用户修改个人信息功能&#xff0c;聊天模块提供即时聊天功能。该项目为前后端分离项目并且后端实现分布式&#xff0c…

蓝桥杯入门即劝退(十九)两两交换链表

-----持续更新蓝桥杯入门系列算法实例-------- 如果你也喜欢Java和算法&#xff0c;欢迎订阅专栏共同学习交流&#xff01; 你的点赞、关注、评论、是我创作的动力&#xff01; -------希望我的文章对你有所帮助-------- 一、题目描述 给你一个链表&#xff0c;两两交换其中…

JavaEE简单示例——<select>中的查询参数传递和结果集封装自动映射关系

简单介绍&#xff1a; 在之前我们在讲SQL映射文件中的映射查询语句的<select>标签的时候&#xff0c;对其中的四个常用属性的讲解并不是那么的透彻&#xff0c;今天就来详细的解释<select>的四个常用属性的具体含义以及<select>标签在进行查询的时候查询参数…

LQB02控制LED灯,74HC138芯片,74HC02芯片,74HC573芯片。

一&#xff0c;硬件图解读。 二&#xff0c;控制LED需要的74HC595程序编程。 三&#xff0c;控制某个LED亮&#xff0c;其他保持不变&#xff0c;或者控制整8个LED&#xff0c;其他不变&#xff1b; 四&#xff0c;读取某个LED的状态&#xff0c;一秒时间读取一次&#xff0c;如…

mapreduce与yarn

文章目录一、MapReduce1.1、MapReduce思想1.2、MapReduce实例进程1.3、MapReduce阶段组成1.4、MapReduce数据类型1.5、MapReduce关键类1.6、MapReduce执行流程1.6.1、Map阶段执行流程1.6.2、Map的shuffle阶段执行流程1.6.3、Reduce阶段执行流程1.7、MapReduce实例WordCount二、…

版本控制软件SVN

SVN学习 1 版本控制软件定义及用途 版本控制软件是为适应软件配置管理的需要&#xff0c;控制软件的修改&#xff0c;减少混乱&#xff0c;提高软件生产效率&#xff0c;其是软件质量保证的重要环节软件配置管理是对软件修改进行标识、组织和控制的技术&#xff0c;用来协调和…

MASA MAUI Plugin (八)Android相册多选照片(Intent 方式)

背景 MAUI的出现&#xff0c;赋予了广大.Net开发者开发多平台应用的能力&#xff0c;MAUI 是Xamarin.Forms演变而来&#xff0c;但是相比Xamarin性能更好&#xff0c;可扩展性更强&#xff0c;结构更简单。但是MAUI对于平台相关的实现并不完整。所以MASA团队开展了一个实验性项…

代码随想录NO49 | 动态规划 _LeetCode1143.最长公共子序列 1035.不相交的线 53. 最大子序和

动态规划 _LeetCode1143.最长公共子序列 1035.不相交的线 53. 最大子序和今天继续子序列问题&#xff01; 1143.最长公共子序列 给定两个字符串 text1 和 text2&#xff0c;返回这两个字符串的最长 公共子序列 的长度。如果不存在 公共子序列 &#xff0c;返回 0 。 一个字符…

docker全解

目录说明docker简介为什么是docker容器与虚拟机比较容器发展简史传统虚拟机技术容器虚拟化技术docker能干什么带来技术职级的变化开发/运维&#xff08;Devops)新一代开发工程师Docker应用场景why docker&#xff1f;docker的优势docker和dockerHub官网Docker安装CentOS Docker…