Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[Backtracing][Linux] Add Linux support to swift-backtrace. #66337

Merged
merged 12 commits into from Jun 7, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
3 changes: 3 additions & 0 deletions include/swift/AST/SemanticAttrs.def
Expand Up @@ -144,5 +144,8 @@ SEMANTICS_ATTR(NO_PERFORMANCE_ANALYSIS, "no_performance_analysis")
// that may cause the user to think there is a bug in the compiler.
SEMANTICS_ATTR(NO_MOVEONLY_DIAGNOSTICS, "sil.optimizer.moveonly.diagnostic.ignore")

// Force the use of the frame pointer for the specified function
SEMANTICS_ATTR(USE_FRAME_POINTER, "use_frame_pointer")

#undef SEMANTICS_ATTR

7 changes: 3 additions & 4 deletions include/swift/Runtime/Backtrace.h
Expand Up @@ -134,7 +134,8 @@ struct BacktraceSettings {

SWIFT_RUNTIME_STDLIB_INTERNAL BacktraceSettings _swift_backtraceSettings;

SWIFT_RUNTIME_STDLIB_SPI SWIFT_CC(swift) bool _swift_isThunkFunction(const char *mangledName);
SWIFT_RUNTIME_STDLIB_SPI
bool _swift_backtrace_isThunkFunction(const char *mangledName);

/// Try to demangle a symbol.
///
Expand All @@ -145,7 +146,6 @@ SWIFT_RUNTIME_STDLIB_SPI SWIFT_CC(swift) bool _swift_isThunkFunction(const char
/// @param outputBuffer is a pointer to a buffer in which to place the result.
/// @param outputBufferSize points to a variable that contains the size of the
/// output buffer.
/// @param status returns the status codes defined in the C++ ABI.
///
/// If outputBuffer is nullptr, the function will allocate memory for the
/// result using malloc(). In this case, outputBufferSize may be nullptr;
Expand All @@ -167,8 +167,7 @@ SWIFT_RUNTIME_STDLIB_SPI
char *_swift_backtrace_demangle(const char *mangledName,
size_t mangledNameLength,
char *outputBuffer,
size_t *outputBufferSize,
int *status);
size_t *outputBufferSize);
#ifdef __cplusplus
} // namespace backtrace
} // namespace runtime
Expand Down
6 changes: 6 additions & 0 deletions lib/IRGen/IRGenSIL.cpp
Expand Up @@ -21,6 +21,7 @@
#include "swift/AST/IRGenOptions.h"
#include "swift/AST/ParameterList.h"
#include "swift/AST/Pattern.h"
#include "swift/AST/SemanticAttrs.h"
#include "swift/AST/SubstitutionMap.h"
#include "swift/AST/Types.h"
#include "swift/Basic/ExternalUnion.h"
Expand Down Expand Up @@ -1835,6 +1836,11 @@ IRGenSILFunction::IRGenSILFunction(IRGenModule &IGM, SILFunction *f)
}
}

// If we have @_semantics("use_frame_pointer"), force the use of a
// frame pointer for this function.
if (f->hasSemanticsAttr(semantics::USE_FRAME_POINTER))
CurFn->addFnAttr("frame-pointer", "all");

// Disable inlining of coroutine functions until we split.
if (f->getLoweredFunctionType()->isCoroutine()) {
CurFn->addFnAttr(llvm::Attribute::NoInline);
Expand Down
50 changes: 50 additions & 0 deletions stdlib/public/Backtracing/ArrayImageSource.swift
@@ -0,0 +1,50 @@
//===--- ArrayImageSource.swift - An image source backed by an Array -------===//
//
// This source file is part of the Swift.org open source project
//
// Copyright (c) 2023 Apple Inc. and the Swift project authors
// Licensed under Apache License v2.0 with Runtime Library Exception
//
// See https://swift.org/LICENSE.txt for license information
// See https://swift.org/CONTRIBUTORS.txt for the list of Swift project authors
//
//===----------------------------------------------------------------------===//
//
// Defines ArrayImageSource, an image source that is backed by a Swift Array.
//
//===----------------------------------------------------------------------===//

import Swift

@_implementationOnly import OS.Libc

enum ArrayImageSourceError: Error {
case outOfBoundsRead(UInt64, UInt64)
}

struct ArrayImageSource<T>: ImageSource {
private var array: Array<T>

public init(array: Array<T>) {
self.array = array
}

public var isMappedImage: Bool { return false }
public var path: String? { return nil }
public var bounds: Bounds? {
return Bounds(base: 0, size: Size(array.count * MemoryLayout<T>.stride))
}

public func fetch<U>(from addr: Address,
into buffer: UnsafeMutableBufferPointer<U>) throws {
try array.withUnsafeBytes{
let size = Size($0.count)
let requested = Size(buffer.count * MemoryLayout<U>.stride)
if addr > size || requested > size - addr {
throw ArrayImageSourceError.outOfBoundsRead(addr, requested)
}

memcpy(buffer.baseAddress!, $0.baseAddress! + Int(addr), Int(requested))
}
}
}