/** Remove a file */ int ypfs_unlink(const char *path) { int ret_code = 0; char* full_path = NULL; sqlite3_stmt *stmt; #ifdef DEBUG if(1){ FILE *f2 = fopen("/opfs/log2.txt", "a"); fprintf(f2, "UNLINK: %s\n", path); fclose(f2); } #endif if ( !hasPermission(CURRENT->uid, path, conn) ) { ret_code = -EACCES; } else { full_path = build_path(path); ret_code = unlink(full_path); } if (!ret_code) { sqlite3_prepare_v2(conn, "DELETE FROM pictures WHERE filename=?", -1, &stmt, NULL); sqlite3_bind_text(stmt, 1, path + last_index_of(path, '/'), -1, SQLITE_TRANSIENT); sqlite3_step(stmt); sqlite3_finalize(stmt); } free(full_path); return ret_code; }
Permission overwritePermissions(const Permission basePermissions, const Server& server, const ServerMember& member, const Channel& channel) { if (hasPermission(basePermissions, Permission::ADMINISTRATOR)) return Permission::ALL; Permission permissions = basePermissions; const std::vector<Overwrite>& overwrites = channel.permissionOverwrites; auto everyoneOverwrites = static_cast<Snowflake<Overwrite>>(server.ID).findObject(overwrites); if (everyoneOverwrites != overwrites.end()) handleOverwrite(permissions, *everyoneOverwrites); //role overwrites Permission allow = NONE; Permission deny = NONE; for (Snowflake<Role> roleID : member.roles) { auto roleOverwrite = static_cast<Snowflake<Overwrite>>(roleID).findObject(overwrites); if (roleOverwrite != overwrites.end()) { allow = allow | roleOverwrite->allow; deny = deny | roleOverwrite->deny; } } handleOverwrite(permissions, allow, deny); //member overwrites auto memberOverwrites = static_cast<Snowflake<Overwrite>>(member.user.ID).findObject(overwrites); if (memberOverwrites != overwrites.end()) handleOverwrite(permissions, *memberOverwrites); return permissions; }
bool PlayerRelationsManager::hasPermission(const Being *const being, const unsigned int flags) const { if (!being) return false; if (being->getType() == ActorType::Player) return hasPermission(being->getName(), flags) == flags; return true; }
int ypfs_rename(const char *path, const char *newpath) { int ret_code = 0; char* full_path; char* new_full_path; sqlite3_stmt *stmt; #ifdef DEBUG if(1){ FILE *f2 = fopen("/opfs/log2.txt", "a"); fprintf(f2, "RENAME: %s TO %s\n", path, newpath); fclose(f2); } #endif full_path = build_path(path); new_full_path = build_path(newpath); if ( !hasPermission(CURRENT->uid, path, conn) ) { ret_code = -EACCES; } else if (!strstr(path, "+private") && strstr(newpath, "+private")) { char* command; asprintf(&command, "/opfs/encode \"%s\" \"%s\" \"%d\"", full_path, new_full_path, CURRENT->uid); ret_code = system(command); if ( WEXITSTATUS(ret_code) ) ret_code = -EACCES; free(command); } else if (strstr(path, "+private") && !strstr(newpath, "+private")) { char* command; asprintf(&command, "/opfs/decode \"%s\" \"%s\" \"%d\"", new_full_path, full_path, CURRENT->uid); ret_code = system(command); if ( WEXITSTATUS(ret_code) ) ret_code = -EACCES; free(command); } else { ret_code = rename(full_path, new_full_path); } if (!ret_code) { sqlite3_prepare_v2(conn, "UPDATE pictures SET filename=? WHERE filename=?", -1, &stmt, NULL); sqlite3_bind_text(stmt, 2, path + last_index_of(path, '/'), -1, SQLITE_TRANSIENT); sqlite3_bind_text(stmt, 1, newpath + last_index_of(newpath, '/'), -1, SQLITE_TRANSIENT); sqlite3_step(stmt); sqlite3_finalize(stmt); } free(full_path); free(new_full_path); return ret_code; }
void TCPClient::sendData(const char* data, std::size_t size, const net::Address& peerAddress) { TraceL << "Send data to " << peerAddress << endl; // Ensure permissions exist for the peer. if (!hasPermission(peerAddress.host())) throw std::runtime_error("No permission exists for peer: " + peerAddress.host()); auto conn = connections().get(peerAddress, nullptr); if (!conn) throw std::runtime_error("No peer exists for: " + peerAddress.toString()); conn->send(data, size); }
void UDPAllocation::onPeerDataReceived(void*, const MutableBuffer& buffer, const net::Address& peerAddress) { //auto source = reinterpret_cast<net::PacketInfo*>(packet.info); TraceL << "Received UDP Datagram from " << peerAddress << endl; if (!hasPermission(peerAddress.host())) { TraceL << "No Permission: " << peerAddress.host() << endl; return; } updateUsage(buffer.size()); // Check that we have not exceeded out lifetime and bandwidth quota. if (IAllocation::deleted()) return; stun::Message message(stun::Message::Indication, stun::Message::DataIndication); // Try to use the externalIP value for the XorPeerAddress // attribute to overcome proxy and NAT issues. std::string peerHost(server().options().externalIP); if (peerHost.empty()) { peerHost.assign(peerAddress.host()); assert(0 && "external IP not set"); } auto peerAttr = new stun::XorPeerAddress; peerAttr->setAddress(net::Address(peerHost, peerAddress.port())); message.add(peerAttr); auto dataAttr = new stun::Data; dataAttr->copyBytes(bufferCast<const char*>(buffer), buffer.size()); message.add(dataAttr); //Mutex::ScopedLock lock(_mutex); TraceL << "Send data indication:" << "\n\tFrom: " << peerAddress << "\n\tTo: " << _tuple.remote() //<< "\n\tData: " << std::string(packet.data(), packet.size()) << endl; server().udpSocket().sendPacket(message, _tuple.remote()); //net::Address tempAddress("58.7.41.244", _tuple.remote().port()); //server().udpSocket().send(message, tempAddress); }
Permission& PermissionManager::addPermission( const String& rName, bool allowed, unsigned int maxItemsAllowed /*= MAXUINT*/, unsigned int maxItemsPerTime /*= MAXUINT*/, double timeSeconds /*= MAXDOUBLE*/ ) { if( !hasPermission( rName ) ) { Permission* permission = new Permission( rName, allowed, maxItemsAllowed, maxItemsPerTime, timeSeconds ); mPermissions.insert( std::make_pair( rName, permission ) ); return *permission; } else { DIVERSIA_EXCEPT( Exception::ERR_DUPLICATE_ITEM, "Permission already exists.", "PermissionManager::addPermission" ); } }
template <typename T> Permission& PermissionManager::addPermission( const String& rName, bool allowed, unsigned int maxItemsAllowed, unsigned int maxItemsPerTime, double timeSeconds, const T& rLowerBounds, const T& rUpperBounds, bool adjustBounds ) { if( !hasPermission( rName ) ) { Permission* permission = new Permission( rName, allowed, maxItemsAllowed, maxItemsPerTime, timeSeconds, rLowerBounds, rUpperBounds, adjustBounds ); mPermissions.insert( std::make_pair( rName, permission ) ); return *permission; } else { DIVERSIA_EXCEPT( Exception::ERR_DUPLICATE_ITEM, "Permission already exists.", "PermissionManager::addPermission" ); } }
Permission getBasePermissions(const Server& server, const ServerMember& member) { if (server.ownerID == member.user.ID) return Permission::ALL; auto everyoneRole = static_cast<Snowflake<Role>>(server.ID).findObject(server.roles); if (everyoneRole == server.roles.end()) return Permission::NONE; Permission permissions = everyoneRole->permissions; for (Snowflake<Role> roleID : member.roles) { auto rolePermissions = roleID.findObject(server.roles); if (rolePermissions != server.roles.end()) permissions = permissions | rolePermissions->permissions; } if (hasPermission(permissions, Permission::ADMINISTRATOR)) return Permission::ALL; return permissions; }
static int ypfs_open(const char *path, struct fuse_file_info *fi) { char* full_path; int f; int ret_code; #ifdef DEBUG if(1){ FILE *f2 = fopen("/opfs/log2.txt", "a"); fprintf(f2, "OPEN: %s\n", path); fclose(f2); } #endif if ( !hasPermission(CURRENT->uid, path, conn) ) { return -EACCES; } #ifdef DEBUG if(!strcmp(path,"/debug")){ return 0; } #endif full_path = build_path(path); if ( (f = open(full_path, fi->flags) ) ) { ret_code = 0; } else { ret_code = -ENOENT; } fi->fh = f; //if ((fi->flags & 3) != O_RDONLY) // return -EACCES; free(full_path); return ret_code; }
void DiscoverySingleDirectoryJob::directoryListingIteratedSlot(QString file, const QMap<QString, QString> &map) { if (!_ignoredFirst) { // The first entry is for the folder itself, we should process it differently. _ignoredFirst = true; if (map.contains("permissions")) { auto perm = RemotePermissions::fromServerString(map.value("permissions")); emit firstDirectoryPermissions(perm); _isExternalStorage = perm.hasPermission(RemotePermissions::IsMounted); } if (map.contains("data-fingerprint")) { _dataFingerprint = map.value("data-fingerprint").toUtf8(); if (_dataFingerprint.isEmpty()) { // Placeholder that means that the server supports the feature even if it did not set one. _dataFingerprint = "[empty]"; } } } else { // Remove <webDAV-Url>/folder/ from <webDAV-Url>/folder/subfile.txt file.remove(0, _lsColJob->reply()->request().url().path().length()); // remove trailing slash while (file.endsWith('/')) { file.chop(1); } // remove leading slash while (file.startsWith('/')) { file = file.remove(0, 1); } std::unique_ptr<csync_file_stat_t> file_stat(new csync_file_stat_t); file_stat->path = file.toUtf8(); file_stat->size = -1; propertyMapToFileStat(map, file_stat.get()); if (file_stat->type == ItemTypeDirectory) file_stat->size = 0; if (file_stat->type == ItemTypeSkip || file_stat->size == -1 || file_stat->remotePerm.isNull() || file_stat->etag.isEmpty() || file_stat->file_id.isEmpty()) { _error = tr("The server file discovery reply is missing data."); qCWarning(lcDiscovery) << "Missing properties:" << file << file_stat->type << file_stat->size << file_stat->modtime << file_stat->remotePerm.toString() << file_stat->etag << file_stat->file_id; } if (_isExternalStorage && file_stat->remotePerm.hasPermission(RemotePermissions::IsMounted)) { /* All the entries in a external storage have 'M' in their permission. However, for all purposes in the desktop client, we only need to know about the mount points. So replace the 'M' by a 'm' for every sub entries in an external storage */ file_stat->remotePerm.unsetPermission(RemotePermissions::IsMounted); file_stat->remotePerm.setPermission(RemotePermissions::IsMountedSub); } QStringRef fileRef(&file); int slashPos = file.lastIndexOf(QLatin1Char('/')); if (slashPos > -1) { fileRef = file.midRef(slashPos + 1); } _results.push_back(std::move(file_stat)); } //This works in concerto with the RequestEtagJob and the Folder object to check if the remote folder changed. if (map.contains("getetag")) { _etagConcatenation += map.value("getetag"); if (_firstEtag.isEmpty()) { _firstEtag = map.value("getetag"); // for directory itself } } }
void UDPAllocation::handleSendIndication(Request& request) { TraceL << "Handle Send Indication" << endl; // The message is first checked for validity. The Send indication MUST // contain both an XOR-PEER-ADDRESS attribute and a DATA attribute. If // one of these attributes is missing or invalid, then the message is // discarded. Note that the DATA attribute is allowed to contain zero // bytes of data. auto peerAttr = request.get<stun::XorPeerAddress>(); if (!peerAttr || (peerAttr && peerAttr->family() != 1)) { ErrorL << "Send Indication error: No Peer Address" << endl; // silently discard... return; } auto dataAttr = request.get<stun::Data>(); if (!dataAttr) { ErrorL << "Send Indication error: No Data attribute" << endl; // silently discard... return; } // The Send indication may also contain the DONT-FRAGMENT attribute. If // the server is unable to set the DF bit on outgoing UDP datagrams when // this attribute is present, then the server acts as if the DONT- // FRAGMENT attribute is an unknown comprehension-required attribute // (and thus the Send indication is discarded). // The server also checks that there is a permission installed for the // IP address contained in the XOR-PEER-ADDRESS attribute. If no such // permission exists, the message is discarded. Note that a Send // indication never causes the server to refresh the permission. // The server MAY impose restrictions on the IP address and port values // allowed in the XOR-PEER-ADDRESS attribute -- if a value is not // allowed, the server silently discards the Send indication. net::Address peerAddress = peerAttr->address(); if (!hasPermission(peerAddress.host())) { ErrorL << "Send Indication error: No permission for: " << peerAddress.host() << endl; // silently discard... return; } // If everything is OK, then the server forms a UDP datagram as follows: // o the source transport address is the relayed transport address of // the allocation, where the allocation is determined by the 5-tuple // on which the Send indication arrived; // o the destination transport address is taken from the XOR-PEER- // ADDRESS attribute; // o the data following the UDP header is the contents of the value // field of the DATA attribute. // The handling of the DONT-FRAGMENT attribute (if present), is // described in Section 12. // The resulting UDP datagram is then sent to the peer. TraceL << "Relaying Send Indication: " << "\r\tFrom: " << request.remoteAddress.toString() << "\r\tTo: " << peerAddress << endl; if (send(dataAttr->bytes(), dataAttr->size(), peerAddress) == -1) { _server.respondError(request, 486, "Allocation Quota Reached"); delete this; } }
bool ContainerPermissions::hasOwnerPermission(uint16 permission) { return hasPermission("owner", permission); }
bool ContainerPermissions::hasPermission(const String& group, uint16 permission) { return hasPermission(group.hashCode(), permission); }