当前位置: 首页 > news >正文

Makefile编译原理 make 中的路径搜索_1

一.make中的路径搜索

问题:在实际的工程项目中,所有的源文件和头文件都放在同一个文件夹中吗?

实验1 : VPATH 引子

mhr@ubuntu:~/work/makefile1/17$ ll
total 28
drwxrwxr-x 4 mhr mhr 4096 Apr 22 00:46 ./
drwxrwxr-x 7 mhr mhr 4096 Apr 22 00:32 ../
drwxrwxrwx 2 mhr mhr 4096 Jan 23  2018 inc/
-rw-rw-r-- 1 mhr mhr  133 Apr 22 00:46 makefile
drwxrwxrwx 2 mhr mhr 4096 Jan 23  2018 src/
mhr@ubuntu:~/work/makefile1/17$ inc/func.h#include <stdio.h>
#include "func.h"void foo()
{printf("void foo() : %s\n", "This file is from inc ...");
}src/func.c#include <stdio.h>
#include "func.h"void foo()
{printf("void foo() : %s\n", HELLO);
}src/main.c#include <stdio.h>
#include "func.h"int main()
{foo();return 0;
}	makefileOBJS := func.o main.ohello.out : $(OBJS)@gcc -o $@ $^@echo "Target File ==> $@"$(OBJS) : %.o : %.c func.h@gcc -o $@ -c $^mhr@ubuntu:~/work/makefile1/17$ 
mhr@ubuntu:~/work/makefile1/17$ make
make: *** No rule to make target 'func.c', needed by 'func.o'.  Stop.
mhr@ubuntu:~/work/makefile1/17$ 

当前makefile: 要创建的可执行程序 hello.out 依赖于 func.o main.o 两个目标文件(当前目录下搜索不到这两个文件),这两个目标文件是通过 规则中的模式替换:

$(OBJS) : %.o : %.c func.h@gcc -o $@ -c $^

解决办法: 

make对VPATH值的处理方式

- 当前文件夹找不到需要的文件时,VPATH就会被使用

- make会在VPATH指定的文件夹中依次搜索文件

- 当多个文件夹存在同名文件时,选择第一次搜索到的文件

实验2 VPATH 初体验, VPATH 只能决定 make 的搜索路径,无法决定命令的搜索路径

OBJS := func.o main.oVPATH := inc srchello.out : $(OBJS)@gcc -o $@ $^@echo "Target File ==> $@"$(OBJS) : %.o : %.c func.h@gcc -o $@ -c $<mhr@ubuntu:~/work/makefile1/17$ 
mhr@ubuntu:~/work/makefile1/17$ make
src/main.c:2:18: fatal error: func.h: No such file or directory#include "func.h"^
compilation terminated.
makefile:11: recipe for target 'main.o' failed
make: *** [main.o] Error 1
mhr@ubuntu:~/work/makefile1/17$ 

显然,这次没有提示: make: *** No rule to make target ‘func.c’, needed by ‘func.o’. Stop.的错误,说明 maka找到了 需要的源文件,即

$(OBJS) : %.o : %.c func.h
找到了 需要的源文件,但是该规则的命令却执行失败。

原因:VPATH 只能决定 make 的搜路径,无法决定命令的搜索路径,他对命令没有任何作用,上面得到的编译错误是因为 gcc 在编译.c文件的时候找不到对应的头文件。

实验3:指定编译命令gcc 需要的文件的搜索路径

OBJS := func.o main.oINC := inc
SRC := src
VPATH := $(INC) $(SRC)
CFLAGS := -I $(INC)hello.out : $(OBJS)@gcc -o $@ $^@echo "Target File ==> $@"$(OBJS) : %.o : %.c func.h  // 为 make 提供搜索路径 :VPATH := $(INC) $(SRC)@gcc $(CFLAGS) -o $@ -c $<  //为 gcc 命令 提供搜索路径,搜索 func.h:-I $(INC)

$(OBJS) : %.o : %.c func.h // 为 make 解释器提供搜索路径 :VPATH := $(INC) $(SRC) ,这样make解释器就得到了需要的文件,并根据规则中的模式替换,生成了最后的规则。

实验4:当多个文件夹存在同名文件时,选择第一次搜索到的文件

假如 inc 头文件文件夹中由于手误也存入了一个 func.c 那么会发生什么

inc/ func.h func.c
这里的func.c 内容如下:

#include <stdio.h>
#include "func.h"void foo()
{printf("void foo() : %s\n", "This file is from inc ...");
}makefile:OBJS := func.o main.oINC := inc
SRC := src
VPATH := $(INC) $(SRC)
CFLAGS := -I $(INC)hello.out : $(OBJS)@gcc -o $@ $^@echo "Target File ==> $@"$(OBJS) : %.o : %.c func.h  // 为 make 提供搜索路径 :VPATH := $(INC) $(SRC)@gcc $(CFLAGS) -o $@ -c $<  //为 gcc 命令 提供搜索路径,搜索 func.h:-I $(INC)mhr@ubuntu:~/work/makefile1/17$ ./hello.out 
void foo() : This file is from inc ...
mhr@ubuntu:~/work/makefile1/17$ 

VPATH 变量告诉make解释器,当在当前目录找不到需要的文件的时候 首先到 inc文件夹中找,如果找不到 再去src文件夹中去找。如果在inc文件夹中找到了需要的文件,那么就不会继续去src文件夹中寻找了。但是inc 中的文件是我们手误放进去的,所以不是我们想要的结果,那么这种情况怎么办呢?

即说明 .h 头文件在 inc文件夹中去找; .c文件到 src文件夹中去找

实验5:vpath(小写) 初探

OBJS := func.o main.o
INC := inc
SRC := src
CFLAGS := -I $(INC)vpath %.h $(INC)
vpath %.c $(SRC)hello.out : $(OBJS)@gcc -o $@ $^@echo "Target File ==> $@"$(OBJS) : %.o : %.c func.h@gcc $(CFLAGS) -o $@ -c $<mhr@ubuntu:~/work/makefile1/17$ 
mhr@ubuntu:~/work/makefile1/17$ ./hello.out 
void foo() : Hello D.T.
mhr@ubuntu:~/work/makefile1/17$ 

相关文章:

Makefile编译原理 make 中的路径搜索_1

一.make中的路径搜索 问题&#xff1a;在实际的工程项目中&#xff0c;所有的源文件和头文件都放在同一个文件夹中吗&#xff1f; 实验1 &#xff1a; VPATH 引子 mhrubuntu:~/work/makefile1/17$ ll total 28 drwxrwxr-x 4 mhr mhr 4096 Apr 22 00:46 ./ drwxrwxr-x 7 mhr m…...

蓝桥杯每日一题------背包问题(一)

点击可观看配套视频讲解 背包问题 阅读小提示&#xff1a;这篇文章稍微有点长&#xff0c;希望可以对背包问题进行系统详细的讲解&#xff0c;在看的过程中如果有任何疑问请在评论区里指出。因为篇幅过长也可以进行选择性阅读&#xff0c;读取自己想要的那一部分即可。 前言…...

面试 JavaScript 框架八股文十问十答第八期

面试 JavaScript 框架八股文十问十答第八期 作者&#xff1a;程序员小白条&#xff0c;个人博客 相信看了本文后&#xff0c;对你的面试是有一定帮助的&#xff01;关注专栏后就能收到持续更新&#xff01; ⭐点赞⭐收藏⭐不迷路&#xff01;⭐ 1&#xff09;实现call、apply…...

【机器学习】单变量线性回归

文章目录 线性回归模型&#xff08;linear regression model&#xff09;损失/代价函数&#xff08;cost function&#xff09;——均方误差&#xff08;mean squared error&#xff09;梯度下降算法&#xff08;gradient descent algorithm&#xff09;参数&#xff08;parame…...

《计算思维导论》笔记:10.4 关系模型-关系运算

《大学计算机—计算思维导论》&#xff08;战德臣 哈尔滨工业大学&#xff09; 《10.4 关系模型-关系运算》 一、引言 本章介绍数据库的基本数据模型&#xff1a;关系模型-关系运算。 二、什么是关系运算 在数据库理论中&#xff0c;关系运算&#xff08;Relational Operatio…...

QT+OSG/osgEarth编译之八十四:osgdb_osg+Qt编译(一套代码、一套框架,跨平台编译,版本:OSG-3.6.5插件库osgdb_osg)

文章目录 一、osgdb_osg介绍二、文件分析三、pro文件四、编译实践一、osgdb_osg介绍 osgDB是OpenSceneGraph(OSG)库中的一个模块,用于加载和保存3D场景数据。osgDB_osg是osgDB模块中的一个插件,它提供了对OSG格式的支持。 OSG格式是OpenSceneGraph库使用的一种二进制文件…...

【Redis快速入门】初识Redis、Redis安装、图形化界面

个人名片&#xff1a; &#x1f43c;作者简介&#xff1a;一名大三在校生&#xff0c;喜欢AI编程&#x1f38b; &#x1f43b;‍❄️个人主页&#x1f947;&#xff1a;落798. &#x1f43c;个人WeChat&#xff1a;hmmwx53 &#x1f54a;️系列专栏&#xff1a;&#x1f5bc;️…...

Linux(Ubuntu) 环境搭建:Nginx

注&#xff1a;服务器默认以root用户登录 NGINX 官方网站地址&#xff1a;https://nginx.org/en/NGINX 官方安装文档地址&#xff1a;https://nginx.org/en/docs/install.html服务器的终端中输入以下指令&#xff1a; # 安装 Nginx apt-get install nginx # 查看版本信息 ngi…...

快速手动完成 VS 编写脚本自动化:如何选取最高效的工作方式?

那些不懂技术的朋友们可能会觉得&#xff0c;写代码写脚本不就是敲敲键盘嘛&#xff0c;搞那么高科技做什么&#xff0c;直接手工点点鼠标不就完事了。 这种看法很常见&#xff0c;但实际情况要复杂得多。 首先&#xff0c;手工操作虽然对于短期和小规模的任务来说似乎更快&am…...

FAST角点检测算法

FAST&#xff08;Features from Accelerated Segment Test&#xff09;角点检测算法是一种快速且高效的角点检测方法。它通过检测每个像素周围的连续像素集合&#xff0c;确定是否为角点。以下是 FAST 角点检测算法的基本流程&#xff1a; FAST 角点检测算法的基本过程主要包括…...

Python中使用opencv-python进行人脸检测

Python中使用opencv-python进行人脸检测 之前写过一篇VC中使用OpenCV进行人脸检测的博客。以数字图像处理中经常使用的lena图像为例&#xff0c;如下图所示&#xff1a; 使用OpenCV进行人脸检测十分简单&#xff0c;OpenCV官网给了一个Python人脸检测的示例程序&#xff0c;…...

牛客网 DP3跳台阶扩展问题

在原始跳台阶问题上&#xff0c;我们知道只走1&#xff0c;2阶台阶的话&#xff0c;可以推出来斐波那契数列的形式进行计算操作。但是&#xff0c;在这里就是1&#xff0c;2&#xff0c;3&#xff0c;...n阶台阶了。其实思路是一样的。 在原始台阶问题&#xff0c;我们的状态方…...

ARM汇编[1] 打印格式化字符串(printf

文章目录 写在前面关键知识简单加减乘除函数调用和循环系统调用栈的使用 GDB调试示例代码 写在前面 如果您对ARM汇编还一无所知的话请先参考ARM汇编hello world 本篇不会广泛详细的列举各种指令&#xff0c;仍然只讲解最关键的部分&#xff0c;然后使用他们来完成一个汇编程序…...

Java 集合、迭代器

Java 集合框架主要包括两种类型的容器&#xff0c;一种是集合&#xff08;Collection&#xff09;&#xff0c;存储一个元素集合&#xff0c;另一种是图&#xff08;Map&#xff09;&#xff0c;存储键/值对映射。Collection 接口又有 3 种子类型&#xff0c;List、Set 和 Queu…...

在 Docker 中启动 ROS2 里的 rivz2 和 rqt 出现错误的解决方法

1. 出现错误&#xff1a; 运行 ros2 run rivz2 rivz2 &#xff0c;报错如下 &#xff1a; No protocol specified qt.qpa.xcb: could not connect to display :1 qt.qpa.plugin: Could not load the Qt platform plugin "xcb" in "" even though it was f…...

使用securecrt+xming通过x11访问ubuntu可视化程序

windows使用securecrtxming通过x11访问ubuntu可视化程序 windows机器IP&#xff1a;192.168.9.133 ubuntu-desktop20.04机器IP&#xff1a;192.168.9.190 windows下载xming并安装 按照图修改xming配置 开始->xming->Xlaunch 完成xming会在右下角后台运行 windows在…...

红队打靶练习:HEALTHCARE: 1

目录 信息收集 1、arp 2、nmap 3、nikto 4、whatweb 目录探测 1、gobuster 2、dirsearch WEB web信息收集 gobuster cms sqlmap 爆库 爆表 爆列 爆字段 FTP 提权 信息收集 本地提权 信息收集 1、arp ┌──(root㉿ru)-[~/kali] └─# arp-scan -l Inte…...

Java IO:概念和分类总结

前言 大家好&#xff0c;我是chowley&#xff0c;刚看完Java IO方面内容&#xff0c;特此总结一下。 Java IO Java IO&#xff08;输入输出&#xff09;是Java编程中用于处理输入和输出的API。它提供了一套丰富的类和方法&#xff0c;用于读取和写入数据到不同的设备、文件和…...

【Linux】基本命令(下)

目录 head指令 && tail指令 head指令 tail指令 find指令 grep指令 zip/unzip指令 tar指令 时间相关的指令 date显示 1.在显示方面&#xff0c;使用者可以设定欲显示的格式&#xff0c;格式设定为一个加号后接数个标记&#xff0c;其中常用的标记列表如下&…...

腾讯云游戏联机服务器配置价格表,4核16G/8核32G/4核32G/16核64G

2024年更新腾讯云游戏联机服务器配置价格表&#xff0c;可用于搭建幻兽帕鲁、雾锁王国等游戏服务器&#xff0c;游戏服务器配置可选4核16G12M、8核32G22M、4核32G10M、16核64G35M、4核16G14M等配置&#xff0c;可以选择轻量应用服务器和云服务器CVM内存型MA3或标准型SA2实例&am…...

Hugo-PaperMod导航菜单异常修复:从故障诊断到性能优化全指南

Hugo-PaperMod导航菜单异常修复&#xff1a;从故障诊断到性能优化全指南 【免费下载链接】hugo-PaperMod A fast, clean, responsive Hugo theme. 项目地址: https://gitcode.com/GitHub_Trending/hu/hugo-PaperMod Hugo-PaperMod作为一款轻量级响应式主题&#xff0c;…...

安装claude code,开始学习强大的AI编程助手

1.首先检查是否安装node.js&#xff08;版本尽量大于22&#xff09; window端输入winr -> cmd 打开终端查看node版本 可以使用nvm去管理nodejs版本&#xff0c;安装方式见 https://blog.csdn.net/m0_56820004/article/details/159585001?spm1011.2415.3001.10575…...

万亿级流量的基石:Kafka 核心原理、大厂面试题解析与实战

第一部分&#xff1a;架构师视角——为什么要选 Kafka&#xff1f;在做技术选型时&#xff0c;我们需要明确 Kafka 的定位&#xff1a;它是一个分布式流式处理平台&#xff0c;而不仅仅是一个消息队列。1. Kafka 的核心优势高吞吐量&#xff1a;单机可支撑每秒百万级别的写操作…...

STM32实战:为小米CyberGear/灵足电机构建机械限位零点与位置模式正弦轨迹

1. 小米CyberGear电机零点丢失问题解析 第一次用小米CyberGear电机做项目时&#xff0c;我就被它断电后零点丢失的问题坑得不轻。早上调好的机械臂&#xff0c;下午上电就歪了30度&#xff0c;这种体验相信很多开发者都遇到过。这其实是大多数伺服电机的通病——断电后编码器位…...

三轴 MEMS 加速度传感器在工业预测性维护中的关键应用

1. 三轴MEMS加速度传感器如何成为工业设备的"听诊器" 想象一下医生用听诊器检查病人心跳的场景。三轴MEMS加速度传感器在工业领域扮演着类似的角色&#xff0c;只不过它"听诊"的对象换成了电机、风机这些设备。这个火柴盒大小的装置&#xff08;303019mm&…...

视觉定位模型Chord实战:基于Qwen2.5-VL,快速搭建多模态目标检测服务

视觉定位模型Chord实战&#xff1a;基于Qwen2.5-VL&#xff0c;快速搭建多模态目标检测服务 1. 项目概述 视觉定位技术正在改变我们与图像交互的方式。Chord模型基于Qwen2.5-VL多模态大模型&#xff0c;能够理解自然语言指令并在图像中精确定位目标对象。想象一下&#xff0c…...

大模型上下文长度的优化策略与应用场景

1. 大模型上下文长度的本质与挑战 当你和ChatGPT聊天时&#xff0c;有没有遇到过它突然"失忆"的情况&#xff1f;比如聊到第20轮对话时&#xff0c;它完全忘记了开头讨论的主题。这就是上下文长度限制导致的典型问题。所谓上下文长度&#xff0c;就是大模型能够记住和…...

从‘飞到红色建筑左边’说起:拆解无人机视觉语言导航(VLN)背后的三大工程难题

从"飞到红色建筑左边"说起&#xff1a;拆解无人机视觉语言导航的工程化困局 当你在测试场地对无人机说出"飞到红色建筑左边"时&#xff0c;这个看似简单的指令背后&#xff0c;是一场跨越模态鸿沟的复杂解码过程。不同于实验室里的完美演示&#xff0c;真实…...

Java开发者必看:Lingbot深度模型服务端集成与高并发处理

Java开发者必看&#xff1a;Lingbot深度模型服务端集成与高并发处理 最近和几个做Java后端的朋友聊天&#xff0c;发现大家对接AI模型服务时&#xff0c;都遇到了类似的头疼事。模型本身效果不错&#xff0c;但一集成到自己的Spring Boot项目里&#xff0c;特别是流量稍微大点…...

如何在ComfyUI中玩转WanVideo:从零到一的视频生成魔法

如何在ComfyUI中玩转WanVideo&#xff1a;从零到一的视频生成魔法 【免费下载链接】ComfyUI-WanVideoWrapper 项目地址: https://gitcode.com/GitHub_Trending/co/ComfyUI-WanVideoWrapper 你是否曾经想过&#xff0c;如果能像搭积木一样轻松创作视频该有多好&#xff…...