【DVWA】19. Insecure CAPTCHA 不安全的验证码(全等级)

news2024/11/18 23:34:40

文章目录

  • 1. Low
    • 1) 源码分析
    • 2)实操
  • 2. Medium
    • 1) 源码分析
    • 2)实操
  • 3. High
    • 1) 源码分析
    • 2)实操
  • 4. Impossible
    • 1) 源码分析

1. Low

1) 源码分析

<?php

if( isset( $_POST[ 'Change' ] ) && ( $_POST[ 'step' ] == '1' ) ) {
    // Hide the CAPTCHA form
    $hide_form = true;

    // Get input
    $pass_new  = $_POST[ 'password_new' ];
    $pass_conf = $_POST[ 'password_conf' ];

    // Check CAPTCHA from 3rd party
    $resp = recaptcha_check_answer(
        $_DVWA[ 'recaptcha_private_key'],
        $_POST['g-recaptcha-response']
    );

    // Did the CAPTCHA fail?
    if( !$resp ) {
        // What happens when the CAPTCHA was entered incorrectly
        $html     .= "<pre><br />The CAPTCHA was incorrect. Please try again.</pre>";
        $hide_form = false;
        return;
    }
    else {
        // CAPTCHA was correct. Do both new passwords match?
        if( $pass_new == $pass_conf ) {
            // Show next stage for the user
            echo "
                <pre><br />You passed the CAPTCHA! Click the button to confirm your changes.<br /></pre>
                <form action=\"#\" method=\"POST\">
                    <input type=\"hidden\" name=\"step\" value=\"2\" />
                    <input type=\"hidden\" name=\"password_new\" value=\"{$pass_new}\" />
                    <input type=\"hidden\" name=\"password_conf\" value=\"{$pass_conf}\" />
                    <input type=\"submit\" name=\"Change\" value=\"Change\" />
                </form>";
        }
        else {
            // Both new passwords do not match.
            $html     .= "<pre>Both passwords must match.</pre>";
            $hide_form = false;
        }
    }
}

if( isset( $_POST[ 'Change' ] ) && ( $_POST[ 'step' ] == '2' ) ) {
    // Hide the CAPTCHA form
    $hide_form = true;

    // Get input
    $pass_new  = $_POST[ 'password_new' ];
    $pass_conf = $_POST[ 'password_conf' ];

    // Check to see if both password match
    if( $pass_new == $pass_conf ) {
        // They do!
        $pass_new = ((isset($GLOBALS["___mysqli_ston"]) && is_object($GLOBALS["___mysqli_ston"])) ? mysqli_real_escape_string($GLOBALS["___mysqli_ston"],  $pass_new ) : ((trigger_error("[MySQLConverterToo] Fix the mysql_escape_string() call! This code does not work.", E_USER_ERROR)) ? "" : ""));
        $pass_new = md5( $pass_new );

        // Update database
        $insert = "UPDATE `users` SET password = '$pass_new' WHERE user = '" . dvwaCurrentUser() . "';";
        $result = mysqli_query($GLOBALS["___mysqli_ston"],  $insert ) or die( '<pre>' . ((is_object($GLOBALS["___mysqli_ston"])) ? mysqli_error($GLOBALS["___mysqli_ston"]) : (($___mysqli_res = mysqli_connect_error()) ? $___mysqli_res : false)) . '</pre>' );

        // Feedback for the end user
        echo "<pre>Password Changed.</pre>";
    }
    else {
        // Issue with the passwords matching
        echo "<pre>Passwords did not match.</pre>";
        $hide_form = false;
    }

    ((is_null($___mysqli_res = mysqli_close($GLOBALS["___mysqli_ston"]))) ? false : $___mysqli_res);
}

?>
  1. 首先,代码检查是否有名为"Change"的POST参数,并且"step"参数的值为1。这意味着该代码是用于处理提交更改密码表单的第一步请求。

  2. 代码将变量$hide_form设置为true。这个变量用于控制是否隐藏验证码表单。

  3. 代码获取输入的新密码和确认密码,并进行比较。如果两个密码不匹配,代码将输出一条错误消息,并将$hide_form设置为false,以便显示密码更改表单供用户重新尝试。

  4. 如果两个密码匹配,代码将调用recaptcha_check_answer函数来验证第三方提供的验证码。这里假设存在一个名为$_DVWA[‘recaptcha_private_key’]的变量用于存储私钥,并且用户在表单中提供了名为g-recaptcha-response的验证码响应。

  5. 如果验证码验证失败(即! r e s p ),代码会输出一条错误消息,并将 resp),代码会输出一条错误消息,并将 resp),代码会输出一条错误消息,并将hide_form设置为false,以便显示验证码表单供用户重新尝试。

  6. 如果验证码验证成功,代码将显示下一步的表单给用户确认密码更改。这个表单包含了一个隐藏的step字段,值为2,以及新密码和确认密码的隐藏字段。

  7. 如果用户点击了确认更改的按钮,代码将进行第二步的处理。

  8. 在第二步中,代码再次将变量$hide_form设置为true。

  9. 代码获取输入的新密码和确认密码,并进行比较。如果两个密码不匹配,代码将输出一条错误消息,并将$hide_form设置为false,以便显示密码更改表单供用户重新尝试。

  10. 如果两个密码匹配,代码将对新密码进行MySQL转义和md5哈希处理,并将密码更新到数据库中。

  11. 如果密码更改成功,代码将输出一条成功的消息。

  12. 如果两个密码不匹配,代码将输出一条失败的消息,并将$hide_form设置为false,以便显示密码更改表单供用户重新尝试。

可以在代码中看出,修改密码时对验证码的验证仅仅是验证了step的值是否为2
在这里插入图片描述

2)实操

由于本地环境配置的原因,此处验证码没有显示,但是我们本来就是要绕过验证码,因此不用管这里
在这里插入图片描述
若不做任何操作,会显示验证码错误
在这里插入图片描述
随后我们重新输入密码并进行抓包,得到的数据包如下

在这里插入图片描述
可以看到最后一行step=1,那这样的话肯定过不了验证码验证
于是我们发送到repeater中将step修改为2重新发包
在这里插入图片描述
可以看到密码修改成功
在这里插入图片描述

2. Medium

1) 源码分析

<?php

if( isset( $_POST[ 'Change' ] ) && ( $_POST[ 'step' ] == '1' ) ) {
    // Hide the CAPTCHA form
    $hide_form = true;

    // Get input
    $pass_new  = $_POST[ 'password_new' ];
    $pass_conf = $_POST[ 'password_conf' ];

    // Check CAPTCHA from 3rd party
    $resp = recaptcha_check_answer(
        $_DVWA[ 'recaptcha_private_key' ],
        $_POST['g-recaptcha-response']
    );

    // Did the CAPTCHA fail?
    if( !$resp ) {
        // What happens when the CAPTCHA was entered incorrectly
        $html     .= "<pre><br />The CAPTCHA was incorrect. Please try again.</pre>";
        $hide_form = false;
        return;
    }
    else {
        // CAPTCHA was correct. Do both new passwords match?
        if( $pass_new == $pass_conf ) {
            // Show next stage for the user
            echo "
                <pre><br />You passed the CAPTCHA! Click the button to confirm your changes.<br /></pre>
                <form action=\"#\" method=\"POST\">
                    <input type=\"hidden\" name=\"step\" value=\"2\" />
                    <input type=\"hidden\" name=\"password_new\" value=\"{$pass_new}\" />
                    <input type=\"hidden\" name=\"password_conf\" value=\"{$pass_conf}\" />
                    <input type=\"hidden\" name=\"passed_captcha\" value=\"true\" />
                    <input type=\"submit\" name=\"Change\" value=\"Change\" />
                </form>";
        }
        else {
            // Both new passwords do not match.
            $html     .= "<pre>Both passwords must match.</pre>";
            $hide_form = false;
        }
    }
}

if( isset( $_POST[ 'Change' ] ) && ( $_POST[ 'step' ] == '2' ) ) {
    // Hide the CAPTCHA form
    $hide_form = true;

    // Get input
    $pass_new  = $_POST[ 'password_new' ];
    $pass_conf = $_POST[ 'password_conf' ];

    // Check to see if they did stage 1
    if( !$_POST[ 'passed_captcha' ] ) {
        $html     .= "<pre><br />You have not passed the CAPTCHA.</pre>";
        $hide_form = false;
        return;
    }

    // Check to see if both password match
    if( $pass_new == $pass_conf ) {
        // They do!
        $pass_new = ((isset($GLOBALS["___mysqli_ston"]) && is_object($GLOBALS["___mysqli_ston"])) ? mysqli_real_escape_string($GLOBALS["___mysqli_ston"],  $pass_new ) : ((trigger_error("[MySQLConverterToo] Fix the mysql_escape_string() call! This code does not work.", E_USER_ERROR)) ? "" : ""));
        $pass_new = md5( $pass_new );

        // Update database
        $insert = "UPDATE `users` SET password = '$pass_new' WHERE user = '" . dvwaCurrentUser() . "';";
        $result = mysqli_query($GLOBALS["___mysqli_ston"],  $insert ) or die( '<pre>' . ((is_object($GLOBALS["___mysqli_ston"])) ? mysqli_error($GLOBALS["___mysqli_ston"]) : (($___mysqli_res = mysqli_connect_error()) ? $___mysqli_res : false)) . '</pre>' );

        // Feedback for the end user
        echo "<pre>Password Changed.</pre>";
    }
    else {
        // Issue with the passwords matching
        echo "<pre>Passwords did not match.</pre>";
        $hide_form = false;
    }

    ((is_null($___mysqli_res = mysqli_close($GLOBALS["___mysqli_ston"]))) ? false : $___mysqli_res);
}

?>

与Low相比多了一步验证,加了对参数passed_captcha的检查,如果为true,则认为已经通过了验证码检查

在这里插入图片描述

2)实操

可以尝试加上这个字段passed_captcha=true绕过,成功在这里插入图片描述

3. High

1) 源码分析

<?php

if( isset( $_POST[ 'Change' ] ) ) {
    // Hide the CAPTCHA form
    $hide_form = true;

    // Get input
    $pass_new  = $_POST[ 'password_new' ];
    $pass_conf = $_POST[ 'password_conf' ];

    // Check CAPTCHA from 3rd party
    $resp = recaptcha_check_answer(
        $_DVWA[ 'recaptcha_private_key' ],
        $_POST['g-recaptcha-response']
    );

    if (
        $resp || 
        (
            $_POST[ 'g-recaptcha-response' ] == 'hidd3n_valu3'
            && $_SERVER[ 'HTTP_USER_AGENT' ] == 'reCAPTCHA'
        )
    ){
        // CAPTCHA was correct. Do both new passwords match?
        if ($pass_new == $pass_conf) {
            $pass_new = ((isset($GLOBALS["___mysqli_ston"]) && is_object($GLOBALS["___mysqli_ston"])) ? mysqli_real_escape_string($GLOBALS["___mysqli_ston"],  $pass_new ) : ((trigger_error("[MySQLConverterToo] Fix the mysql_escape_string() call! This code does not work.", E_USER_ERROR)) ? "" : ""));
            $pass_new = md5( $pass_new );

            // Update database
            $insert = "UPDATE `users` SET password = '$pass_new' WHERE user = '" . dvwaCurrentUser() . "' LIMIT 1;";
            $result = mysqli_query($GLOBALS["___mysqli_ston"],  $insert ) or die( '<pre>' . ((is_object($GLOBALS["___mysqli_ston"])) ? mysqli_error($GLOBALS["___mysqli_ston"]) : (($___mysqli_res = mysqli_connect_error()) ? $___mysqli_res : false)) . '</pre>' );

            // Feedback for user
            echo "<pre>Password Changed.</pre>";

        } else {
            // Ops. Password mismatch
            $html     .= "<pre>Both passwords must match.</pre>";
            $hide_form = false;
        }

    } else {
        // What happens when the CAPTCHA was entered incorrectly
        $html     .= "<pre><br />The CAPTCHA was incorrect. Please try again.</pre>";
        $hide_form = false;
        return;
    }

    ((is_null($___mysqli_res = mysqli_close($GLOBALS["___mysqli_ston"]))) ? false : $___mysqli_res);
}

// Generate Anti-CSRF token
generateSessionToken();

?>

只要g-recaptcha-response和请求头的HTTP_USER_AGENT是符合约定的就行
在这里插入图片描述

2)实操

抓包直接改成这两个值就行g-recaptcha-response=hidd3n_valu3,HTTP_USER_AGENT=reCAPTCHA
修改g-recaptcha-response参数以及User-Agent
在这里插入图片描述

4. Impossible

1) 源码分析

<?php

if( isset( $_POST[ 'Change' ] ) ) {
    // Check Anti-CSRF token
    checkToken( $_REQUEST[ 'user_token' ], $_SESSION[ 'session_token' ], 'index.php' );

    // Hide the CAPTCHA form
    $hide_form = true;

    // Get input
    $pass_new  = $_POST[ 'password_new' ];
    $pass_new  = stripslashes( $pass_new );
    $pass_new  = ((isset($GLOBALS["___mysqli_ston"]) && is_object($GLOBALS["___mysqli_ston"])) ? mysqli_real_escape_string($GLOBALS["___mysqli_ston"],  $pass_new ) : ((trigger_error("[MySQLConverterToo] Fix the mysql_escape_string() call! This code does not work.", E_USER_ERROR)) ? "" : ""));
    $pass_new  = md5( $pass_new );

    $pass_conf = $_POST[ 'password_conf' ];
    $pass_conf = stripslashes( $pass_conf );
    $pass_conf = ((isset($GLOBALS["___mysqli_ston"]) && is_object($GLOBALS["___mysqli_ston"])) ? mysqli_real_escape_string($GLOBALS["___mysqli_ston"],  $pass_conf ) : ((trigger_error("[MySQLConverterToo] Fix the mysql_escape_string() call! This code does not work.", E_USER_ERROR)) ? "" : ""));
    $pass_conf = md5( $pass_conf );

    $pass_curr = $_POST[ 'password_current' ];
    $pass_curr = stripslashes( $pass_curr );
    $pass_curr = ((isset($GLOBALS["___mysqli_ston"]) && is_object($GLOBALS["___mysqli_ston"])) ? mysqli_real_escape_string($GLOBALS["___mysqli_ston"],  $pass_curr ) : ((trigger_error("[MySQLConverterToo] Fix the mysql_escape_string() call! This code does not work.", E_USER_ERROR)) ? "" : ""));
    $pass_curr = md5( $pass_curr );

    // Check CAPTCHA from 3rd party
    $resp = recaptcha_check_answer(
        $_DVWA[ 'recaptcha_private_key' ],
        $_POST['g-recaptcha-response']
    );

    // Did the CAPTCHA fail?
    if( !$resp ) {
        // What happens when the CAPTCHA was entered incorrectly
        echo "<pre><br />The CAPTCHA was incorrect. Please try again.</pre>";
        $hide_form = false;
    }
    else {
        // Check that the current password is correct
        $data = $db->prepare( 'SELECT password FROM users WHERE user = (:user) AND password = (:password) LIMIT 1;' );
        $data->bindParam( ':user', dvwaCurrentUser(), PDO::PARAM_STR );
        $data->bindParam( ':password', $pass_curr, PDO::PARAM_STR );
        $data->execute();

        // Do both new password match and was the current password correct?
        if( ( $pass_new == $pass_conf) && ( $data->rowCount() == 1 ) ) {
            // Update the database
            $data = $db->prepare( 'UPDATE users SET password = (:password) WHERE user = (:user);' );
            $data->bindParam( ':password', $pass_new, PDO::PARAM_STR );
            $data->bindParam( ':user', dvwaCurrentUser(), PDO::PARAM_STR );
            $data->execute();

            // Feedback for the end user - success!
            echo "<pre>Password Changed.</pre>";
        }
        else {
            // Feedback for the end user - failed!
            echo "<pre>Either your current password is incorrect or the new passwords did not match.<br />Please try again.</pre>";
            $hide_form = false;
        }
    }
}

// Generate Anti-CSRF token
generateSessionToken();

?>

首先,代码检查是否有名为"Change"的POST参数。这意味着该代码是用于处理提交更改密码表单的请求。

然后,代码调用checkToken函数来验证防跨站请求伪造(Anti-CSRF)令牌。checkToken函数接受三个参数: R E Q U E S T [ ′ u s e r t o k e n ′ ] , _REQUEST['user_token'], REQUEST[usertoken]_SESSION[‘session_token’]和’index.php’。这里的目的是确保提交的请求是合法的,并且用户已经通过先前的身份验证。

代码将变量$hide_form设置为true。这个变量用于控制是否隐藏验证码表单。

代码获取输入的新密码,并对其进行处理。它首先从$_POST[‘password_new’]获取密码,然后使用stripslashes函数去除可能的反斜杠转义,接着使用mysqli_real_escape_string函数对密码进行MySQL转义,最后使用md5函数进行哈希处理。

代码获取确认密码,并对其进行与新密码相同的处理过程。

代码获取当前密码,并对其进行与新密码相同的处理过程。

代码调用recaptcha_check_answer函数来验证第三方提供的验证码。这里假设存在一个名为$_DVWA[‘recaptcha_private_key’]的变量用于存储私钥,并且用户在表单中提供了名为g-recaptcha-response的验证码响应。

如果验证码验证失败(即! r e s p ),代码会输出一条错误消息,并将 resp),代码会输出一条错误消息,并将 resp),代码会输出一条错误消息,并将hide_form设置为false,以便显示验证码表单供用户重新尝试。

如果验证码验证成功,代码将查询数据库以验证当前密码是否正确。它使用准备好的语句来选择users表中与当前用户和当前密码匹配的记录。如果查询返回一行结果(即$data->rowCount() == 1),则表示当前密码正确。

如果新密码与确认密码匹配并且当前密码正确,代码将更新数据库中的密码。它使用准备好的语句将新密码更新到与当前用户匹配的记录中。

如果密码更改成功,代码将输出一条成功的消息。

如果新密码与确认密码不匹配或当前密码不正确,代码将输出一条失败的消息,并将$hide_form设置为false,以便显示密码更改表单供用户重新尝试。

最后,代码调用generateSessionToken函数生成一个新的防跨站请求伪造(Anti-CSRF)令牌,以便在下一次请求中使用。

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

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

相关文章

WPF图表库LiveCharts的使用

这个LiveCharts非常考究版本&#xff0c;它有非常多个版本&#xff0c;.net6对应的是LiveChart2 我这里的wpf项目是.net6&#xff0c;所以安装的是这三个&#xff0c;搜索的时候要将按钮“包括愈发行版”打勾 git&#xff1a;https://github.com/beto-rodriguez/LiveCharts2?…

BUGKU-WEB never_give_up

题目描述 题目截图如下&#xff1a; 进入场景看看&#xff1a; 解题思路 F12查看请求和响应&#xff0c;查找线索 相关工具 base64解码URL解码Burp Suit抓包 解题步骤 F12查看请求和响应&#xff0c;发现一行注释包含一个文件名称【1p.html】&#xff0c;这应该就是提…

GaN HEMTs在电力电子应用中的交叉耦合与基板电容分析与建模

来源&#xff1a;Analysis and Modeling of Cross-Coupling and Substrate Capacitances in GaN HEMTs for Power-Electronic Applications&#xff08; TED 17年&#xff09; 摘要 本文提出了一种考虑了基板电容与场板之间交叉耦合效应的场板AlGaN/GaN高电子迁移率晶体管(HE…

RabbitMQ自学笔记——消息可靠性问题

1.发送者的可靠性 1.1生产者重连 有时由于网络波动等原因&#xff0c;发送方一次可能没有连接上RabbitMQ&#xff0c;我们可以配置发送方的连接失败重试机制。但需要注意的是&#xff1a;SpringAMQP提供的重试机制是阻塞式的重试&#xff0c;也就是说多次重试等待的过程中&am…

[JAVAEE]—进程和多线程的认识

文章目录 什么是线程什么是进程进程的组成什么是pcb 进程概括线程线程与进程的关系线程的特点 创建线程创建线程方法创建线程的第二种方法对比 其他的方式匿名内部类创建线程匿名内部类创建Runable的子类lambda表达式创建一个线程 多线程的优势 什么是线程 什么是进程 首先想…

iOS 判断触摸位置是否在图片的透明区域

装扮功能系列&#xff1a; Swift 使用UIScrollerView 实现装扮功能&#xff08;基础&#xff09;Swift 使用UIScrollerView 实现装扮功能&#xff08;拓展&#xff09;iOS 判断触摸位置是否在图片的透明区域 背景 在装扮功能中&#xff0c;一般都是长按使道具进入编辑状态&…

ES分布式搜索-使用RestClient操作索引库

RestClient操作索引库 1、什么是RestClient&#xff1f; ES官方提供了各种不同语言的客户端&#xff0c;用来操作ES。这些客户端的本质就是组装DSL语句&#xff0c;通过http请求发送给ES。官方文档地址&#xff1a;Elasticsearch Clients官方文档 2、利用JavaRestClient实现…

软考高级:软件架构风格-闭环控制概念和例题

作者&#xff1a;明明如月学长&#xff0c; CSDN 博客专家&#xff0c;大厂高级 Java 工程师&#xff0c;《性能优化方法论》作者、《解锁大厂思维&#xff1a;剖析《阿里巴巴Java开发手册》》、《再学经典&#xff1a;《Effective Java》独家解析》专栏作者。 热门文章推荐&am…

Python 查找PDF中的指定文本并高亮显示

在处理大量PDF文档时&#xff0c;有时我们需要快速找到特定的文本信息。本文将提供以下三个Python示例来帮助你在PDF文件中快速查找并高亮指定的文本。 查找并高亮PDF中所有的指定文本查找并高亮PDF某个区域内的指定文本使用正则表达式搜索指定文本并高亮 本文将用到国产第三方…

Java学习笔记(11)

面向对象进阶 Static 静态变量 所有对象一起共享&#xff0c;就用static修饰 不属于对象&#xff0c;属于类的 可以用 类名.静态变量 “”&#xff1b;赋值 但是 对象.静态变量也可以访问到内容 Static内存图 Student这个类的字节码文件加载到方法区&#xff0c;并在内…

企业计算机服务器中了eking勒索病毒怎么办?Eking勒索病毒解密工具流程

网络数据安全问题一直是众多企业关心的主要话题&#xff0c;网络在为企业提供便利的同时&#xff0c;也为企业数据安全带来未知的隐患。近日&#xff0c;云天数据恢复中心接到许多企业求助&#xff0c;企业的计算机服务器遭到了eking勒索病毒攻击导致企业计算机服务器系统瘫痪无…

操作系统——cpu、内存、缓存介绍

一、内存是什么 内存就是系统资源的代名词&#xff0c;它是其他硬件设备与 CPU 沟通的桥梁&#xff0c; 计算机中的所有程序都在内存中运行。其作用是暂时存放CPU的运算数据&#xff0c;以及与硬盘交换的数据。也是相当于CPU与硬盘沟通的桥梁。只要计算机在运行&#xff0c;CP…

YOLOv9实例分割教程|(一)训练教程

专栏介绍&#xff1a;YOLOv9改进系列 | 包含深度学习最新创新&#xff0c;主力高效涨点&#xff01;&#xff01;&#xff01; 一、创建数据集及数据配置文件 创新一个文件夹存放分割数据集&#xff0c;包含一个images和labels文件夹。标签格式如下所示&#xff1a; 创新数据集…

Netty线程模型详解

文章目录 概述单Reactor单线程模型单Reactor多线程模型主从Reactor多线程模型 概述 Netty的线程模型采用了Reactor模式&#xff0c;即一个或多个EventLoop轮询各自的任务队列&#xff0c;当发现有任务时&#xff0c;就处理它们。Netty支持单线程模型、多线程模型和混合线程模型…

1、计划任务介绍

Windows计划任务介绍 1、含义&#xff1a; 简单点就是定时执行任务。 在许多场景下&#xff0c;我们定时执行一些任务。比如&#xff1a;定时拉取、备份文件&#xff0c;更新代码等等操作。 WinR打开运行框&#xff0c;输入&#xff1a;control schedtasks&#xff0c;就会…

SAR ADC系列4——比较器的Transient noise仿真--等效输入噪声

仿真出等效输入噪声 加一个快于实际工作的时钟频率&#xff1b;在输入端加一个DC的差&#xff08;比如一端是0.5VDD&#xff0c;另外一端加0.5VDD0.2MV)计算仿真时间内的correct counting number&#xff0c;比如时钟频率是200MHz&#xff0c;仿真时间是5us&#xff0c;那么应…

IMX8MM -- Yocto构建遇见的错误及解决方法:

IMX8MM Yocto构建遇见的错误及解决方法&#xff1a; 1 bison-3.0.4 error2 Opencv BB_NO_NETWORK Error &#xff1a;3 Yocto构建时出现U-boot 问题4 Yocto构建时出现Linux kernel编译问题5 wayland-native6 cross-localedef-native7 wayland-protocols8 mesa 硬件&#xff1a;…

[论文精读]Dynamic Coarse-to-Fine Learning for Oriented Tiny Object Detection

论文网址&#xff1a;[2304.08876] 用于定向微小目标检测的动态粗到细学习 (arxiv.org) 论文代码&#xff1a;https://github.com/ChaselTsui/mmrotate-dcfl 英文是纯手打的&#xff01;论文原文的summarizing and paraphrasing。可能会出现难以避免的拼写错误和语法错误&…

android MMKV数据持久化缓存集合

前言 最近在使用mmkv缓存的时候 发现没有集合缓存 非常不方便 自己写一个方法 MMKV public class MmkvUtils {private MmkvUtils() {throw new UnsupportedOperationException("u cant instantiate me...");}public static void init() {MMKV.initialize(LeoUtils…

C语言从入门到熟悉------第三阶段

数组 什么是数组呢&#xff1f;顾名思义数组就是很多数的组合&#xff01;那么这些数有没有什么要求呢&#xff1f;是不是不管什么数组合在一起都是数组呢&#xff1f;第一&#xff0c;这些数的类型必须相同&#xff01;第二&#xff0c;这些数在内存中必须是连续存储的。也就…