C++不同平台下的RTTI实现

给定一个含有虚函数的对象的地址,找到对应的类名,不同平台下方法也不同,这是由于RTTI实现并没有统一的标准。

Linux:

Linux

#include <iostream>
#include <typeinfo>class Person
{
public:virtual void func(){std::cout << typeid(*this).name() << std::endl;}
};const char* ClassName(void* address)
{uintptr_t* objPtr = reinterpret_cast<uintptr_t*>(address);uintptr_t* vftablePtr = reinterpret_cast<uintptr_t*>(*objPtr);std::type_info* ti = reinterpret_cast<std::type_info*>(*(vftablePtr - 1));return ti->name();
}int main()
{Person p;std::cout << ClassName(&p) << std::endl;std::cout << typeid(p).name() << std::endl;
}

运行结果:

6Person
6Person

其中,Person代表类名,6表示的是类名的长度。


Windows x86:

Windows x86

#include <iostream>
#include <typeinfo>class Person
{
public:virtual void func(){std::cout << typeid(*this).name() << std::endl;}
};const char* ClassMangledName(void* address)
{uintptr_t* objPtr = reinterpret_cast<uintptr_t*>(address);uintptr_t* vftablePtr = reinterpret_cast<uintptr_t*>(*objPtr);uintptr_t* rttiObject = reinterpret_cast<uintptr_t*>(*(vftablePtr - 1));std::type_info* ti = reinterpret_cast<std::type_info*>(*(rttiObject + 3));const char* className = ti->name();return className;
}int main()
{Person p;std::cout << ClassMangledName(&p) << std::endl;std::cout << typeid(p).name() << std::endl;
}

运行结果:

class Person
class Person

Windows x64:

Windows x64

#include <iostream>
#include <ehdata.h>
#include <rttidata.h>class Person
{
public:virtual void func(){std::cout << typeid(*this).name() << std::endl;}
};const char* ClassMangledName(void* address)
{uintptr_t* objPtr = reinterpret_cast<uintptr_t*>(address);uintptr_t* vftablePtr = reinterpret_cast<uintptr_t*>(*objPtr);_RTTICompleteObjectLocator* rttiLocator = reinterpret_cast<_RTTICompleteObjectLocator*>(*(vftablePtr - 1));uintptr_t imageBase = reinterpret_cast<uintptr_t>(rttiLocator) - rttiLocator->pSelf;TypeDescriptor* typeDescriptor = reinterpret_cast<TypeDescriptor*>(imageBase + rttiLocator->pTypeDescriptor);const char* classMangledName = typeDescriptor->name;return classMangledName;
}int main()
{Person p;std::cout << ClassMangledName(&p) << std::endl;std::cout << typeid(p).raw_name() << std::endl;
}

运行结果:

.?AVPerson@@
.?AVPerson@@

打印的结果是raw name,也就是未修饰的名字。

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

如若内容造成侵权/违法违规/事实不符,请联系编程知识网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

2023.11.28-电商平台建设03 - 大数据调优手段

1.优化手段 1.1分桶表 HIVE的分桶本质上就是MR的分区操作 建表语句: create table 表名(字段 类型,.... ) clustered by(分桶字段) [sorted by (字段 [asc | desc])] into N buckets --- 定义分桶表核心语句 row format...... 分桶的作用 1) 进行数据采样工作 1.1) …

C++ Boost 异步网络编程基础

Boost库为C提供了强大的支持&#xff0c;尤其在多线程和网络编程方面。其中&#xff0c;Boost.Asio库是一个基于前摄器设计模式的库&#xff0c;用于实现高并发和网络相关的开发。Boost.Asio核心类是io_service&#xff0c;它相当于前摄模式下的Proactor角色。所有的IO操作都需…

STM32CubeIDE(CUBE-MX hal库)----串口通信

提示&#xff1a;文章写完后&#xff0c;目录可以自动生成&#xff0c;如何生成可参考右边的帮助文档 文章目录 前言一、CUBE-MX可视化配置二、发送数据和接收数据1.HAL库串口的阻塞模式和非阻塞模式2.HAL库串口阻塞模式数据发送函数3.HAL库串口阻塞模式数据接收函数4.HAL库串口…

氯碱工业盐水精制除钙镁树脂

#氯碱工业盐水精制除钙镁树脂 ​氯碱工业是生产烧碱、氯气、氢气及其衍生产品的基础化工工业之一&#xff0c;在经济发展中具有重要地位&#xff0c;对国防建设和经济具有重要作用。 目前&#xff0c;氯碱工业是采用电解饱和食盐水的方法来制取&#xff0c;无论氯碱工业采用何种…

临近年关,准备好迎接春运了吗?易知微来助力

除夕不放假&#xff1f;&#xff1f;&#xff01;&#xff01;作为中国传统节日的春节&#xff0c;除夕属于是其中最热闹的时间点之一&#xff0c;虽然对于假期如此“不合理的”安排&#xff0c;大家都无可奈何&#xff0c;但是对家人的思念和对传统文化的传承&#xff0c;春节…

Leetcode—739.每日温度【中等】

2023每日刷题&#xff08;四十二&#xff09; Leetcode—739.每日温度 单调栈实现思想 从右到左实现代码 class Solution { public:vector<int> dailyTemperatures(vector<int>& temperatures) {int n temperatures.size();stack<int> st;vector<i…

【产品设计】SaaS平台产品架构设计

产品架构是基于业务架构的&#xff0c;那么做产品架构前&#xff0c;需要对业务架构有哪些清晰的了解呢&#xff1f; 当我们去搜索“架构”&#xff0c;可以得到很多的架构图片&#xff0c;比如组织架构、业务架构、数据架构、技术架构、安全架构、产品架构、部署架构等。 什么…

Zookeeper 实战 | Zookeeper 和Spring Cloud相结合解决分布式锁、服务注册与发现、配置管理

专栏集锦&#xff0c;大佬们可以收藏以备不时之需&#xff1a; Spring Cloud 专栏&#xff1a;http://t.csdnimg.cn/WDmJ9 Python 专栏&#xff1a;http://t.csdnimg.cn/hMwPR Redis 专栏&#xff1a;http://t.csdnimg.cn/Qq0Xc TensorFlow 专栏&#xff1a;http://t.csdni…

消失的数字,旋转数组(leetcode 一题多解)

目录 一、消失的数字 思路一&#xff08;暴力求解&#xff09;代码实现&#xff1a; 思路二&#xff08;数列的思想&#xff09;代码实现&#xff1a; 思路三&#xff08;异或的运用&#xff09;代码实现&#xff1a; 二、轮转数组 思路一&#xff08;暴力求解&#xff09…

网络和Linux网络_6(应用层)HTTPS协议(加密解密+中间人攻击+证书)

目录 1. HTTPS协议介绍 1.1 加密解密和秘钥的概念 1. 2 为什么要加密 2. 对称加密和非对称加密 2.1 只使用对称加密 2.2 只使用非对称加密 2.3 双方都使用非对称加密 2.4 使用非对称加密对称加密 2.5 中间人攻击MITM 3. 证书的概念和HTTPS的通信方式 3.1 CA认证机构…

java对象 转换成json字符串 工具类 jackson

jackson概述 Jackson 是一个用于处理 JSON 数据的 Java 库&#xff0c;由 FasterXML 公司开发和维护。它提供了一组功能强大的 API&#xff0c;用于在 Java 对象和 JSON 数据之间进行高效的序列化&#xff08;将对象转换为 JSON 格式&#xff09;和反序列化&#xff08;将 JSO…

『VUE3后台—大事件管理系统』

项目地址&#xff1a;https://gitee.com/csheng-gitee/vue3-big-event-admin 技术栈&#xff1a;VUE3 Pinia Pnpm&#xff08;本项目暂不用 typescript&#xff09; 一、前期准备工作 1、创建项目 npm install -g pnpm pnpm create vue2、ESLint 配置 (1) 禁用 prettier 插…