将std :: bind与std :: function结合使用时,我无法理解一些细微之处.
我已将问题最小化到以下代码段:
#include <functional>
#include <iostream>
void bar(int x) {
std::cout << "Hello." << std::endl;
}
int main(int argc, char* argv[])
{
std::function<void(int)> f1 = std::bind(bar, std::placeholders::_1);
// CRASHES with clang, works fine in VS2010 and VS2012
std::function<void()> f2 = std::bind(f1, 1);
f2();
return 0;
}
Run Code Online (Sandbox Code Playgroud)
注意显式转换到std ::函数<>(代替std::function<void()>与auto施工时f2工作正常).
f2通过f1在OS X(XCode 5.0.1,OS X 10.9 SDK)上使用Clang 复制对象崩溃创建,但与VS2010/VS2012一起正常工作.在一个非常长的callstack之后,代码崩溃了一个EXC_BAD_ACCESS - 注意这是在构造函数对象时,而不是在调用它时.
这是库实现中的错误还是我的代码有问题?
解决方法是显式调用operator ()成员,如下所示:
std::function<void()> f2 = …Run Code Online (Sandbox Code Playgroud) 我正在使用boost :: asio进行一个项目,其中同一台机器上的两个进程使用TCP/IP进行通信.一个生成要由另一个读取的数据,但我遇到的问题是间歇性地没有数据通过连接发送.基于异步tcp echo服务器示例,我将其简化为下面的一个非常简单的示例.
这些流程(下面的源代码)很好地开始,从发送方到接收方以快速的速度提供数据.然后突然间,根本没有数据被传递大约五秒钟.然后再次传送数据,直到下一个无法解释的暂停.在这五秒钟内,进程占用0%的CPU,并且没有其他进程似乎特别做任何事情.暂停总是相同的长度 - 五秒钟.
我试图弄清楚如何摆脱这些摊位以及导致它们的原因.

请注意在运行过程中如何有三次CPU使用率下降 - "运行"是服务器进程和客户端进程的单次调用.在这些逢低期间,没有提供数据.运行之间的下降次数和时间有所不同 - 有时甚至没有下降,有时很多.
我可以通过改变读缓冲区的大小来影响这些停顿的"概率" - 例如,如果我使读缓冲区成为发送块大小的倍数,则看起来这个问题几乎消失了,但并非完全消失.
我用Visual Studio 2005编译了下面的代码,使用了Boost 1.43和Boost 1.45.我已经在Windows Vista 64位(四核)和Windows 7 64位(四核和双核)上进行了测试.
服务器接受连接,然后只读取和丢弃数据.每当执行读取时,都会发出新的读取.
客户端连接到服务器,然后将一堆数据包放入发送队列.在此之后,它一次写入一个数据包.只要写入完成,就会写入队列中的下一个数据包.一个单独的线程监视队列大小,并每秒将其打印到stdout.在io停顿期间,队列大小保持完全相同.
我曾尝试使用scatter io(在一次系统调用中写入多个数据包),但结果是一样的.如果我在Boost中禁用IO完成端口BOOST_ASIO_DISABLE_IOCP,问题似乎就会消失,但代价是吞吐量明显降低.
// Example is adapted from async_tcp_echo_server.cpp which is
// Copyright (c) 2003-2010 Christopher M. Kohlhoff (chris at kohlhoff dot com)
//
// Start program with -s to start as the server
#ifndef _WIN32_WINNT
#define _WIN32_WINNT 0x0501
#endif
#include …Run Code Online (Sandbox Code Playgroud) 在 Windows 上,可以有一个服务,允许在用户上下文中运行的客户端使用套接字或管道连接到它,然后模拟连接用户以代表该用户进行操作,例如访问只有用户有权访问(或确保没有其他文件被访问)。
在 Mac OS X 上完成此操作的等效方法是什么(Linux 也很有趣)?我会假设 set*uid 函数会以某种方式用于此目的吗?
但是,当用户连接到套接字时,如何验证我想要模拟的用户并设置 uid 呢?
此外, set*uid 函数似乎会影响整个进程,这使得它们难以在多线程守护进程中使用。对于 Mac OS X/Linux 上的此类服务,是否有不同的常用设计模式?
编辑:pmjordan 的回答似乎解决了 set*uid per-process-only 问题,以及如何通过 Mac OS X 上的 Unix 域套接字传递用户凭据的问题?似乎通过使用 unix 域套接字而不是普通套接字来解决实际的身份验证问题。
我对在跨平台分布式系统中处理用户身份验证和授权可以使用哪些策略感兴趣.我希望能够将系统中的操作标记为属于某个用户,并且仅允许某些用户执行某些操作.
背景: 该系统目前仅在Windows下使用,其中由用户发起的操作当前仅被标记为来自用户的特定机器.一个动作基本上涉及使用cpu进行一些计算并返回结果.
目前没有任何授权,也没有用户身份验证(或计算机之间).系统作为具有低权限的服务运行(使用NETWORK SERVICE帐户).数据不敏感,允许本地网络上的所有用户使用该系统的内容.
该系统既可以部署在同构Windows域设置中,也可以部署在没有域控制器的工作组中,也可以与域的混合以及不属于域的一堆工作计算机一起部署.
问题
为了向系统添加功能,例如收集每个用户的使用统计信息或显示谁正在使用计算机,有必要跟踪个人用户.除此之外,如果某些用户只允许执行某些操作(例如更改系统的某些设置),则还需要某种形式的授权.
我非常了解Windows的这种做法,并且在Windows中使用内置的身份验证和授权功能,在同类Windows域设置中添加此类功能将非常简单.这也消除了将仅对该特定系统有效的特殊帐户分配给系统的需要 - 一旦用户正常登录,就可以完成所有认证和授权而无需任何额外的用户交互.
但是,如果系统应该能够在Mac OSX上运行怎么办?还是Linux?如果它应该在Windows域中的某些用户和OSX上的其他用户以及运行Linux的某些工作机器的混合环境中运行,该怎么办?(实际系统可以移植到所有这些系统并处理跨平台通信等).我对在这些平台上处理身份验证和授权的方式知之甚少,并且不了解在平台之间进行交互时如何实现这一点.
在像这样的分布式系统中,是否有任何好的策略可用于跨平台用户身份验证和授权?注意这里"跨平台"的双重用途 - 既可以为不同的平台编译程序,也可以在平台之间进行交互.
我将问题标记为C++,因为这是系统编写的语言,但我愿意接受任何可以使用C++进行交互的内容.任何想法(包括狂野的建筑变化)都是受欢迎的!
更新:
能够实现的有趣内容的一个例子:
用户A登录到计算机1,这是一台Windows计算机.
用户A打开系统的管理界面,选择机器2(Linux系统)并调整设置.系统验证用户A实际上是否具有足够的权限以允许执行此操作.
由于A在他/她登录时已经验证了他的身份,因此希望允许他/她更改此设置而无需提供额外的凭证.
c++ architecture authentication authorization cross-platform
我想序列化boost :: signals2信号的多线程调用,以确保来自对象的状态变化的通知以明确定义的顺序到达插槽.
背景
我有一个在多线程程序中具有内部状态的对象.内部状态的某些部分对程序的其他部分很有意义,并且对象通过使用boost :: signals2信号来暴露状态更改,类似于:
class ObjectWithState {
public:
enum State {
STATE_A,
STATE_B,
STATE_C,
};
void OnEvent() {
State newState;
{
boost::lock_guard<boost::mutex> lock(m_Mutex);
// Process event and change state
m_State = ...;
newState = m_State;
}
m_OnStateChanged(newState);
}
// method to allow external objects to connect to the signal etc
private:
boost::signals2::signal<void (State) > m_OnStateChanged;
boost::mutex m_Mutex;
State m_State;
};
Run Code Online (Sandbox Code Playgroud)
问题
如果OnEvent处理程序有多个并发调用,这可能会导致侦听器收到有关状态更改的通知,而不是实际发生的更改.状态本身受上面的互斥锁保护,因此实际状态是明确定义的.但是,在对信号的调用中不能保持互斥锁,因为这可能导致死锁.这意味着信号的实际调用可能以任何顺序发生,而我要求它们以与实际发生状态变化相同的顺序被调用.
处理此问题的一种方法是从信号中删除状态,并通知侦听器状态已更改.然后,他们可以查询对象的状态,并获得对象在触发信号时的状态或以后的状态.在我的场景中,需要告知侦听器所有状态更改,因此此方法在此处不起作用.
我的下一个方法是如下:
class ObjectWithState {
public:
enum State { …Run Code Online (Sandbox Code Playgroud) 我试图让 Qt WebView 显示一个嵌入为 Qt 资源的 html 文件,但我似乎无法让它工作。我创建了一个新的 Qt Quick 应用程序并添加了一个简单的 qml 文件:
import QtQuick 2.0
import QtWebKit 3.0
Rectangle {
id: content
width: 800
height: 600
color: "black"
WebView {
id: webView
anchors.fill: parent
url: "qrc:/res/test.html"
}
}
Run Code Online (Sandbox Code Playgroud)
然后我(使用设计器)创建了一个如下所示的资源文件:
<RCC>
<qresource prefix="/res">
<file>test.html</file>
</qresource>
</RCC>
Run Code Online (Sandbox Code Playgroud)
并创建了一个简单的 test.html 文件(与 .qrc 文件在同一目录中):
<html>
<head><title>Hello</title></head>
<body>
<h1>Hello World!</h1>
</body>
</html>
Run Code Online (Sandbox Code Playgroud)
结果只是一个空白的白色窗口。如果我http://www.stackoverflow.com在 qml 文件中使用常规 url ( ) 作为它工作的 url - 该页面将显示。如果我使用嵌入图像的名称 ( qrc:/qt-project.org/mac/cursors/images/pluscursor.png),则会显示该图像。
在我看来,好像确实添加了 html 文件(至少在我枚举嵌入式资源时会列出),但我对 Qt 资源系统的理解有限,所以我很可能误解了一些基本的东西。
谁能告诉我我做错了什么?
更新:我已经验证,如果我尝试告诉 …
我正在尝试在 Mac OS X 下将 aio_* 函数用于异步文件 IO,但是我在将某种形式的用户数据获取到信号处理程序中时遇到了问题。
这是设置操作的代码:
class aio_context {
public:
aio_context(int fildes, boost::uint64_t offset,
const MyBufferClassPtr &buffer)
{
// The aiocb struct must be zeroed
memset(&m_aiocb, 0, sizeof(struct aiocb));
// Set what to do
m_aiocb.aio_fildes = fildes;
m_aiocb.aio_buf = buffer->data();
m_aiocb.aio_nbytes = buffer->size();
m_aiocb.aio_offset = offset;
// Set notification
m_aiocb.aio_sigevent.sigev_notify = SIGEV_SIGNAL;
m_aiocb.aio_sigevent.sigev_signo = SIGUSR1;
// ATTEMPT TO SET A VALUE THAT CAN BE READ IN THE HANDLER
m_aiocb.aio_sigevent.sigev_value.sival_ptr = this;
}
struct aiocb* GetAiocbp()
{
return …Run Code Online (Sandbox Code Playgroud) 是否可以从 launchd 守护进程使用execve ?我想将进程制作成守护进程,然后使用 fork() 和 execve 启动多个子进程,但创建 launchd 守护进程的文档指出“调用 fork 后跟 exec”是不行的。这是否意味着我无法从守护进程创建子进程?
我正在检查用于实现通信协议的 Flatbuffers。当收到一条消息时,就我而言,它可能包含许多不同的表。如果我理解正确,在 Flatbuffers 中实现这一点的方法是使用一个“根”表,该表在联合中包含每个可能的不同表。
就我而言,我已经知道传入类型(类型是标题的一部分)=> 我不一定需要能够将每种类型放在单个表中。但是,似乎不可能将多个表标记为“根”类型。这意味着,如果我已经定义了表Foo并且Bar我只能获得反序列化的一个GetFoo()或一个GetBar()方法,但不能同时获得两者。
我假设也可以将定义拆分到不同的模式文件中,但由于它们将共享一些子类,因此我还需要一个共享模式文件来用于公共定义。对于简单的情况,这似乎比必要的要复杂一些。
是否有另一种方法可以使用 Flatbuffers 反序列化多种不同类型?
我试图使用以下代码控制远程计算机上的服务:
// Error checking omitted for brevity
HANDLE hToken = NULL;
// user = username with no domain specification
// domain = targetmachine when targetting computer outside of domain
LogonUser(user, domain, password,
LOGON32_LOGON_NEW_CREDENTIALS, LOGON32_PROVIDER_WINNT50, &hToken);
ImpersonateLoggedOnUser(hToken);
SC_HANDLE hSc = OpenSCManager(targetmachine,
SERVICES_ACTIVE_DATABASE, SC_MANAGER_ALL_ACCESS);
Run Code Online (Sandbox Code Playgroud)
从使用当前登录用户的凭据以及使用其他凭据时,从本地域中的计算机运行并在同一域上定位计算机时,此方法可以正常工作.
但是,当我尝试定位不在任何域上的计算机时,OpenSCManager如果我指定除了SC_MANAGER_CONNECT所需访问之外的任何内容,则调用将失败并拒绝访问.从域外的计算机中定位域计算机(对于作为目标计算机上的本地管理员的域用户,使用用户/域/密码组合).从域外的计算机定位域外的计算机不起作用.
用户/密码是针对目标计算机上管理员组的成员,因此帐户权限不应存在问题.
我已经检查了scmanager安全描述符sc -sdshow scmanager,它对于域计算机和非域计算机是相同的.两者都运行Windows 7 64位.
我也测试过使用psexec,它有相同的症状,即在域计算机之间工作正常但在目标非域计算机时不能.
我还测试了在目标计算机上禁用RPC over TCP并重新启动它,因为这被描述为访问被拒绝错误的可能原因,但这似乎没有帮助.我还测试了在targetmachine上禁用Windows防火墙,但没有变化.
是否需要启用某些设置才能使远程服务配置正常工作?
我试图检测以前安装的包的版本号是什么。然而,burn 似乎没有找到它,尽管它适当地检测到它将进行重大升级。
这是我的 bundle xml 的相关部分的样子:
<?define BUNDLE_UPGRADE_CODE=my_upgrade_code_guid?>
<Wix xmlns="http://schemas.microsoft.com/wix/2006/wi" xmlns:util="http://schemas.microsoft.com/wix/UtilExtension">
<Bundle UpgradeCode="$(var.BUNDLE_UPGRADE_CODE)" DisableModify="yes" ...>
<util:ProductSearch UpgradeCode="$(var.BUNDLE_UPGRADE_CODE)" Variable="PreviousVersion" />
<BootstrapperApplicationRef ... />
<Chain>
<ExePackage Id="my_exe_package".../>
<MsiPackage Id="my_msi_package" .../>
</Chain>
</Bundle>
</Wix>
Run Code Online (Sandbox Code Playgroud)
想法是 ProductSearch 应该使用升级代码检测任何产品并将版本号放在变量中PreviousVersion以供以后使用。但是,burn 似乎没有检测到任何带有此升级代码的现有产品,而是始终将版本设置为“ 0.0.0.0”。以下是日志文件的相关部分(为清晰起见进行了一些编辑):
...: Detect begin, 2 packages
...: Product or related product not found: {my_upgrade_code_guid}
...: Setting version variable 'PreviousVersion' to value '0.0.0.0'
...: Detected related bundle: {previous_bundle_product_code}, type: Upgrade, scope: PerMachine, version: 1.0.0.0, operation: MajorUpgrade
...: Detected related package: {previous_msi_product_code}, scope: PerMachine, …Run Code Online (Sandbox Code Playgroud) 好的,所以我有一个类Vector:
#include <cstdlib>
class Vec
{
private:
size_t size;
int * ptab;
public:
Vec(size_t n);
~Vec() {delete [] ptab;}
size_t size() const {return size;}
int & operator[](int n) {return ptab[n];}
int operator[](int n) const {return ptab[n];}
void operator=(Vec const& v);
};
inline Vec::Vec(size_t n) : size(n), ptab(new int[n])
{ }
Run Code Online (Sandbox Code Playgroud)
问题是在我的一个作业练习中我必须扩展构造函数def,所以所有元素都将用零初始化.我以为我知道基础但不能通过这个动态阵列-.-
PS.sry语法和其他错误;)